Code Lab 개편중

Posted at 2011/01/11 01:51 // in Old Data (자료 정리중) // by drDorothy
일관성이 없어서 모든 글을 수정 중.

카테고리, 글 내용, 저질 게시물 삭제 등 예정.
2011/01/11 01:51 2011/01/11 01:51

Neural Net을 이용한 숫자인식 프로그램

Posted at 2009/06/17 14:41 // in Old Data (자료 정리중) // by drDorothy
인공지능 마지막 숙제...
뭔가 새로운 분야였지만...
막상.. 어찌 응용을 해야할지 ㅡ_ㅡ;;......
이것과 시스템은 어떻게 연결 할 수 있을까 ㅡ_ㅡ.........
#include 
#include 
#include 
#include 

#include "NumberSet.h"
TRAININGSET g_trainingSet[MAX_DATA]; // 트레이닝 데이터

// 전체 뉴런 개수 설정
#define INPUT_NEURON		32
#define HIDDEN_NEURON		20
#define OUTPUT_NEURON		10

// 인풋에서 히든, 히든에서 출력 레이어 그래프 (바이어스도 포함)
double g_weight_i2h[INPUT_NEURON+1][HIDDEN_NEURON];
double g_weight_h2o[HIDDEN_NEURON+1][OUTPUT_NEURON];

/* 내부 그래프용 노드 */
double g_inputs[INPUT_NEURON]  = {0,};
double g_hidden[HIDDEN_NEURON] = {0,};
double g_desire[OUTPUT_NEURON] = {0,};
double g_output[OUTPUT_NEURON] = {0,};

/* Unit Errors */
double g_err_output[OUTPUT_NEURON] = {0,};
double g_err_hidden[HIDDEN_NEURON] = {0,};

// 학습률 - c값
#define LEARN_RATE		0.2

// 시그모이드 함수 & 편미분 함수
double sigmoid( double val )           { return (1.0 / (1.0 + exp(-val))); }
double sigmoidDerivative( double val ) { return ( val * (1.0 - val) ); }

// 랜덤한 가중치 부여
void RandomWeight( void ) {
	int hidden, input, out;
	#define RAND_WEIGHT	(((float)rand() / (float)RAND_MAX) - 0.5)

	for (input=0; input < INPUT_NEURON+1; input++)
		for (hidden=0; hidden < HIDDEN_NEURON; hidden++)
			g_weight_i2h[input][hidden] = RAND_WEIGHT;

	for (hidden = 0 ; hidden < HIDDEN_NEURON+1 ; hidden++)
		for (out = 0 ; out < OUTPUT_NEURON ; out++)
			g_weight_h2o[hidden][out] = RAND_WEIGHT;
}

// 각 뉴럴의 실제 계산 및 전달 (현재 뉴럴의 최종 아웃풋이 g_output에 저장됨)
void feedForward( void )
{
	double sum;
	int input, hidden, out;

	// 인풋에서 히든레이어 계산
	for (hidden=0; hidden < HIDDEN_NEURON; hidden++)
	{
		// 각 뉴런의 inputs * weight의 총 합을 계산
		for (sum=.0, input=0; input < INPUT_NEURON; input++)
			sum += g_inputs[input] * g_weight_i2h[input][hidden];

		sum += g_weight_i2h[INPUT_NEURON][hidden]; // 바이어스
		g_hidden[hidden] = sigmoid(sum); // 시그모이드 함수 적용
	}

	// 히든에서 출력레이어 계산
	for (out=0; out < OUTPUT_NEURON; out++)
	{
		// 각 뉴런의 hidden * weight의 총 합을 계산
		for (sum=.0,hidden=0; hidden < HIDDEN_NEURON; hidden++)
			sum += g_hidden[hidden] * g_weight_h2o[hidden][out];

		sum += g_weight_h2o[HIDDEN_NEURON][out]; // 바이어스
		g_output[out] = sigmoid( sum ); // 시그모이드 함수 적용
	}
}

// 오차 수집후 가중치 조율
void backPropagate( void )
{
	int input, hidden, out;

	// 출력의 에러 콜렉팅
	for (out=0; out < OUTPUT_NEURON; out++)

		// Desire 값과 실제 나온 값의 차를 결과의 미분값으로 곱함
		g_err_output[out] = (g_desire[out] - g_output[out]) * sigmoidDerivative(g_output[out]);

	// 히든의 에러 콜렉팅
	for (hidden=0; hidden < HIDDEN_NEURON; hidden++)
	{
		g_err_hidden[hidden] = .0;

		// 먼저 출력의 에러를 가중치를 곱하여 모두 합산
		for (out=0; out < OUTPUT_NEURON; out++)
			g_err_hidden[hidden] += g_err_output[out] * g_weight_h2o[hidden][out];

		// 출력에서와 같은 방식으로 합산된것을 히든의 결과값의 미분값을 넣음
		g_err_hidden[hidden] *= sigmoidDerivative( g_hidden[hidden] );
	}

	// 출력의 가중치 조정
	for (out=0; out < OUTPUT_NEURON; out++)
	{
		// 새로운 가중치는 출력의 에러에 히든의 값을 곱하여 LEARN RATE 만큼 적용하여 더함
		for (hidden=0; hidden < HIDDEN_NEURON; hidden++)
			g_weight_h2o[hidden][out] += LEARN_RATE * g_err_output[out] * g_hidden[hidden];

		g_weight_h2o[HIDDEN_NEURON][out] += LEARN_RATE * g_err_output[out]; // 바이어스
	}

	// 히든의 가중치 조정
	for (hidden=0; hidden < HIDDEN_NEURON; hidden++)
	{
		// 출력과 동일 히든의 에러에 실제넣은값을 곱하여 LEARN RATE 만큼 적용하여 더함
		for (input=0; input < INPUT_NEURON; input++)
			g_weight_i2h[input][hidden] += LEARN_RATE * g_err_hidden[hidden] * g_inputs[input];

		g_weight_i2h[INPUT_NEURON][hidden] += LEARN_RATE * g_err_hidden[hidden]; // 바이어스
	}
}

// 가장 정답에 가까운거 집어내기
int select( double *array )
{
	int i, index=0;
	double max = array[index];

	for (i=1; i < OUTPUT_NEURON; i++) // 답은 찾아야 할테니..
		if (array[i] > max)
			max = array[i], index = i;

	return index;
}

// 실제 프로그램 시작
int main(void)
{
	double err;
	int i,j, training=0, loop=0;
	unsigned int temp;
	char test[33] = " 11 1  11  1   1   1  1  1  1111"; // 임의의 문자..

	srand( (unsigned) time(NULL) );
	RandomWeight(); // 랜덤한 가중치 부여

	// 트레이닝 데이터 초기화
	for (i=0; i<10; i++) {
		for (j=0; j0; i--)
				swap(&g_trainingSet[i], &g_trainingSet[rand()%i]);

		for (i=0,temp=g_trainingSet[training].data; i>=1)
			g_inputs[i] = temp & MASK1; // 인풋 비트 연결

		for (i=0; i>= 1)
		g_inputs[i] = temp & MASK1; // 입력값 연결

	feedForward();
	printf("실제값: %d, 추정값: %d\n", 2, select(g_output));
	return 0;
}
2009/06/17 14:41 2009/06/17 14:41

쓰레기 File Lock 구현..

Posted at 2009/06/13 13:17 // in Old Data (자료 정리중) // by drDorothy
SP 과제의 내용중 하나인....
File Lock 구현하라는거.. ㅡ_ㅡ....
(세마포어는 찝찝해서 안쓰긴 했지만....... 통지메세지 걸어버리는것도 반칙인가 ㅡ_ㅡ?!..)
코드에 시그널 처리부분을 날림제작해서.. 레이스 컨디션이 생기지만.. 일단 패스..
(시연시 문제 없었으니 조용히 넘어가면 되는거임 ㅡ_ㅡ......)

그리고.. goto가 얼마나 편리한데.. PL시간엔 자꾸 욕을하니.. ㅡ_ㅡ..
(그래도 사용하는 센스..)
#define _GNU_SOURCE
#include 
#include 

#include "db.h"

// 시그널 부분 초기화
void db_lock_init( void )
{
	struct sigaction	act;

	// SIGIO 처리
	act.sa_sigaction = VoidHandler;
	sigemptyset(&act.sa_mask);
	act.sa_flags = 0;
	sigaction(SIGIO, &act, NULL);

	// SIGALRM 처리 (혹시모를 상황에 대비 - 0 이면 사용 안함)
#if DB_LOCK_TIMEOUT > 0
	act.sa_sigaction = VoidHandler;
	sigemptyset(&act.sa_mask);
	act.sa_flags = 0;
	sigaction(SIGALRM, &act, NULL);
#endif
}

// Lock을 실제로 거는 부분
int db_lock( IN char *path, DWORD offset, DWORD size )
{
	pid_t			pid;
	DIR				*pDir;
	struct dirent	*pDirInfo;
	char			buffer[64];
	int				fd; // Lock 풀린거 감지용

	DWORD			offset_i, size_i;

	// 오프셋별 접근을 막기 위한 초기 작업
	sprintf(buffer, "%s.lck", path);
	mkdir(buffer, 0700);
start:
	if ((pDir=opendir(buffer)) == NULL)
		return -1;

	sprintf(buffer, "%s/%d_%d", buffer, offset, size);

	// 만일 이미 파일이 있다면.. 누군가 쓰는거..
	if ((fd=open(buffer, O_WRONLY | O_CREAT | O_EXCL, 0600)) == -1) {
		closedir(pDir);
		goto Lock;
	}

	// 파일이 없어도 겹치는 부분이 있는지 확인해 봐야함
	// Lock의 범위 검증 시작
	while ((pDirInfo = readdir(pDir)) != NULL)
	{
		// 디렉토리 건너뛰고
		if (strcmp(pDirInfo->d_name, ".") == 0 ||
			strcmp(pDirInfo->d_name, "..") == 0)
			continue;

		sscanf(pDirInfo->d_name, "%u_%u", &offset_i, &size_i);

		//  방금 만든것도 건너뛰고
		if (offset_i == offset && size_i == size)
			continue;

		// 범위가 겹친다면 문제가 좀 있죠..
		if ( (offset_i <= offset && offset < offset_i + size_i) ||
			 (offset_i <= offset+size-1 && offset+size-1 < offset_i + size_i) )
		{
			closedir(pDir);
			close(fd);
			unlink(buffer);
			goto Lock;
		}
	}

	// Lock이 성공적으로 걸림
	// 만일 프로세스가 Lock을 걸어버리고 죽는다면..
	// pid 확인해서 Lock 정리 작업	
	closedir(pDir);
	pid = getpid();
	write(fd, &pid, sizeof(pid_t));
	return close(fd);

Lock: // Lock이 걸린 경우에 대한 처리 (Lock이 풀림을 기다림)
      // 반드시 생각해야 하는것..!! fd는 제한되어있으니 관리바람

	sprintf(buffer, "%s.lck", path);
	fd = open(buffer, O_RDONLY);
	fcntl(fd, F_NOTIFY, DN_DELETE);

	// 타임아웃이 설정되어 있다면 알람으로 강제로 깨움
#if DB_LOCK_TIMEOUT > 0
	alarm(DB_LOCK_TIMEOUT);
#endif

	pause();
	close(fd);

	goto start; // 깨어나면.. 다시 Lock을 시도
}

// Lock을 해제
int db_unlock( IN char *path, DWORD offset, DWORD size )
{
	int		fd;
	pid_t	pid;
	char	buffer[64];

	fprintf(stderr, "[DB] File unlocking 시작.\n");
	sprintf(buffer, "%s.lck/%d_%d", path, offset, size);

	if (access(buffer, F_OK) != 0)
		return -1;

	if ((fd=open(buffer, O_RDONLY)) == -1)
		return -1;

	if (read(fd, &pid, sizeof(pid_t)) != sizeof(pid_t)) {
		close(fd);
		return -1;
	}

	close(fd);

	if (pid != getpid())
		return -1;

	return unlink(buffer);
}
2009/06/13 13:17 2009/06/13 13:17

지하철 최단경로

Posted at 2009/06/06 16:14 // in Old Data (자료 정리중) // by drDorothy
그냥 정확하게 숙제의 요구조건만 맞춘것.. ㅡ_ㅡ..
다익스트라 알고리즘으로 최단경로의 시간 계산만 함..
교수님이 아예 복잡한 상황을 만들어내는 인풋은 안준다고 했으니..
고런 인풋은 쌩깜.. (대략 허접함..)

숏코딩 할까말까 고민하다가..
결국 이상한 코드가 되어버림 ㅡ_ㅡ.....


#include 
#include 
#include 

#define BYTE unsigned char
#define WORD unsigned short

// 태그를 넣으면 인덱스 나옴
#define TTOI(tag) IndexTag[tag]

WORD *IndexTag; // 바로 참조 가능하도록한 인덱스

typedef union Tag {
	WORD val;
	struct {
		WORD Line:4;
		WORD stNo:6;
		WORD junk:6;
	};
} Tag;
Tag* SetTag(Tag *t, int l, int n) { t->Line=l;t->stNo=n;t->junk=0x00;return t; }

BYTE** CreateSubwayMap(int IndexSize, int LineSize, Tag* Line, int TranSize, Tag** Tran, int weight)
{
	int i, j;
	Tag tag1, tag2;
	BYTE** a; // 만들어질 공간

	// 배열 공간 잡기 (실제 존재하는 노선에 대해서만 생성됨)
	a = (BYTE**) malloc(sizeof(BYTE*) * IndexSize);
	for (i=0; ival] = k++;	// 이렇게 하면 Tag를 넣으면 인덱스가 나옴
}

int main(void)
{
	int TotalLines, TotalTransfer, TotalInput, weight;
	int IndexSize=0, TagSize=0;
	int i, j, k, p, t1, t2, start, min;
	int *leng, *Y; // 정점까지의 거리 및 확정 노드

	Tag tag1, tag2;
	Tag *LineInfo, **TranInfo; // 파일로 부터 읽어들인 기본자료들..
	BYTE** graph; // 전역 작업 공간

	FILE *fp = fopen("input.txt", "rt");

	// 일단은 노선 정보 먼저 읽어놓고 작업크기 계산
	fscanf(fp, "%d", &TotalLines);
	LineInfo = (Tag*) calloc(TotalLines, sizeof(Tag));

	for (i=0; ival);

		// 작업공간을 만들기
		graph = CreateSubwayMap(IndexSize, TotalLines, LineInfo, TotalTransfer, TranInfo, weight);

		// 보조 작업용 배열 선언 및 초기화 (다익스트라 알고리즘의 시작)
		Y = (int*) calloc(IndexSize, sizeof(int));
		leng = (int*) malloc(sizeof(int)*IndexSize);
		for (j=0; jval)]);
		for (j=0; j
						
2009/06/06 16:14 2009/06/06 16:14

인공지능 발표용 자료 (최종)

Posted at 2009/05/08 09:12 // in Old Data (자료 정리중) // by drDorothy
신은 나에게 ppt만드는 재주를 주심을 깜박하셨다.. ㅡ_ㅡ
이건 뭐.. 거의 발로 만든 수준이군 ㅡ_ㅡ;;...
앞으로 ppt 만드는건 최대한 피해야지 ㅡ_ㅡ..

15-Puzzle은 IDA*
Rubik's Cube는 Best First Search..

2009/05/08 09:12 2009/05/08 09:12