Desc :

 

 


Source Code :

#include <stdio.h>
#include <winsock2.h>

#pragma comment(lib,"wsock32.lib")

void main()
{
	SOCKET s;	// 소켓 디스크립터
	WSADATA wsaData;
	SOCKADDR_IN sin;	// 소켓 구조체

	if (WSAStartup(WINSOCK_VERSION, &wsaData) != 0)
	{
		printf("WSAStartup 실패, 에러코드 = %d\n", WSAGetLastError());
		return;
	}

	s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);	// TCP/IP용 소켓 생성

	if (s == INVALID_SOCKET)
	{
		printf("소켓 생성 실패, 에러코드: %d \n", WSAGetLastError());
		WSACleanup();	//WS2_32.DLL의 사용을 종료합니다
		return;
	}

	sin.sin_family = AF_INET;	// 주소 체계 설정
	sin.sin_addr.s_addr = inet_addr("127.0.0.1");	// 접속 주소 설정
	sin.sin_port = htons(2001);	// 포트 번호 설정

	if (connect(s, (struct sockaddr*)&sin, sizeof(sin)) != 0)
	{
		printf("접속 실패, 에러코드 = %u \n", WSAGetLastError());
		closesocket(s);
		WSACleanup();
		return;
	}

	if (closesocket(s) != 0)
	{
		printf("소켓 제거 실패, 에러코드 = %u \n", WSAGetLastError());
		WSACleanup();
		return;
	}

	if (WSACleanup() != 0)
	{
		printf("WSACleanup 실패, 에러코드 = %u \n", WSAGetLastError());
		return;
	}

	puts("127.0.0.1의 2001번 포트에 접속을 성공하였습니다.");
}

 


Result :

10061 대상컴퓨터에서 연결을 거부했다.............

'C' 카테고리의 다른 글

[C] TCP/IP 초기화하기  (1) 2021.02.18
[C] 268 주소록 (아직 작성 안함)  (0) 2021.02.18
[C] 267 이중 링크드 리스트 구현하기  (1) 2021.02.17
[C] 266 단일 링크드 리스트 구현  (0) 2021.02.17
[C] 265 큐 구현  (0) 2021.02.17

Desc :

TCP/IP - 프로그램에서 원거리의 컴퓨터와 상호 데이터를 주고받기 위한 통신 규약

TCP/IP 통신 프로그램은 흔히 소켓 프로그램이라고도 한다

 

TCP/IP를 통해 데이터를 주고 받으려면

파일을 입출력 할 때 처럼

소켓의 개방 - socket()

소켓의 제거 - closesocket() 함수가 반드시 필요

 

윈도우 소켓 프로그램에서는 여러 종류의 소켓 버전이 사용되기 때문에

소켓 버전을 설정 - WSAStartup()

해제 - WSAClean() 함수도 필수적

 

TCP/IP에 사용되는 모든 함수들은 <winsock2.h>에 선언되어 있다

일반적인 C Runtime Library 가 아니기 때문에

wsock32.lib를 반드시 포함

#pragma comment (특정 라이브러리 파일을 포함시킬 때 사용)

 

 

 

 

소켓 디스크립터: 소켓을 개방, 송수신, 종료할 때 사용

WSADATA wsaData: 현재 사용 가능한 윈속 정보를 얻기 위해 정의, 소켓버전 값 저장됨

 


Source Code :

#include <stdio.h>
#include <winsock2.h>

#pragma comment(lib,"wsock32.lib")

void main()
{
	SOCKET s;	// 소켓 디스크립터
	WSADATA wsaData;

	if (WSAStartup(WINSOCK_VERSION, &wsaData) != 0)
	{
		printf("WSAStartup 실패, 에러코드 = %d\n", WSAGetLastError());
		return;
	}
    
	puts(wsaData.szDescription); 	// 사용하고있는 윈속 버전
	puts(wsaData.szSystemStatus);	// 사용하고있는 윈속의 상태

	s = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);	// TCP/IP용 소켓 개방

	if (s == INVALID_SOCKET)
	{
		printf("소켓 생성 실패, 에러코드: %d \n", WSAGetLastError());
		WSACleanup();	//WS2_32.DLL의 사용을 종료합니다
		return;
	}

	if (closesocket(s) != 0)	// 소켓 제거
	{
		printf("소켓 제거 실패, 에러코드 = %u \n", WSAGetLastError());
		WSACleanup();	//WS2_32.DLL의 사용을 종료합니다
		return;
	}

	if (WSACleanup() != 0)	// 소켓에서 사용했던 자원들 비우기
	{
		printf("WSACleanup 실패, 에러코드 = %u \n", WSAGetLastError());
		return;
	}

	puts("윈속을 사용할 수 있습니다.");
}

 


Result :

Desc :

 

 


Source Code :

#include <stdio.h>
#include <malloc.h>
#include <string.h>

int add_list(char* name);
void print_list(void);
void remove_list(void);

typedef struct tagLinkedList
{
	char name[30];

	struct tagLinkedList *prev;
	struct tagLinkedList *next;
}ADDR;

ADDR *g_pAddrHead = NULL;

void main()
{
	add_list("Kim");
	add_list("Choi");

	print_list();
	remove_list();
}

int add_list(char* name)
{
	ADDR *plocal;

	if (g_pAddrHead == NULL)
	{
		g_pAddrHead = malloc(sizeof(ADDR));

		if (g_pAddrHead == NULL)
		{
			return 0;	// 할당실패
		}

		g_pAddrHead->prev = NULL;
		g_pAddrHead->next = NULL;
	}
	else
	{
		plocal = malloc(sizeof(ADDR));

		if (plocal == NULL)
		{
			return 0; // 할당 실패
		}
		
		g_pAddrHead->next = plocal;
		plocal->prev = g_pAddrHead;
		g_pAddrHead = plocal;
		g_pAddrHead->next = NULL;
	}

	strcpy(g_pAddrHead->name, name);

	return 1;
}

void print_list(void)
{
	int count = 1;
	ADDR *plocal;

	plocal = g_pAddrHead;

	while (plocal->prev) //리스트의 맨 처음으로 이동
	{
		plocal = plocal->prev;
	}

	while (plocal)
	{
		printf("No.%d: ", count++);
		puts(plocal->name);
		plocal = plocal->next;
	}
}

void remove_list(void)
{
	ADDR *plocal;	// 다음 노드 주소 저장

	while (g_pAddrHead->prev) // 리스트 맨 처음으로 이동
	{
		g_pAddrHead = g_pAddrHead->prev;
	}
	
	while (g_pAddrHead)	// 마지막 노드까지 메모리 반환
	{
		plocal = g_pAddrHead->next;

		free(g_pAddrHead);	// 현재 노드 메모리 반환 

		g_pAddrHead = plocal;
	}

	g_pAddrHead = NULL; // 재사용을 위한 초기화
}

조건문에서 == 연산자를 =로 썼다. 바보...


Result :

'C' 카테고리의 다른 글

[C] TCP/IP 초기화하기  (1) 2021.02.18
[C] 268 주소록 (아직 작성 안함)  (0) 2021.02.18
[C] 266 단일 링크드 리스트 구현  (0) 2021.02.17
[C] 265 큐 구현  (0) 2021.02.17
[C] 264 스택구현  (0) 2021.02.17

Desc :

도저히 말로는 설명을 못하겠다,,,


Source Code :

#include <stdio.h>
#include <malloc.h>
#include <string.h>

int add_list(char* name, char* tel, char* addr);
void print_list(void);
void remove_list(void);

typedef struct tagLikedList
{
	char name[30];
	char tel[30];
	char addr[100];

	struct tagLikedList *next; // 다음 자료가 위치한 번지를 저장하기 위해 사용
}ADDR;

ADDR *g_pAddrHead = NULL; // 링크드 리스트의 첫번째 노드

void main()
{
	add_list("홍길동", "1111", "서울특별시 종로구");
	add_list("홍길동", "2222", "서울특별시 강서구");
	add_list("Mr.Kim", "3333", "서울특별시 구로구");
	add_list("김C", "4444", "서울특별시 강동구");
	add_list("최C", "5555", "대전광역시 동구");

	print_list();
	remove_list();
}

int add_list(char* name, char* tel, char* addr)
{
	ADDR *plocal;	// 현재 데이터를 저장하기 위함
	ADDR *pn = g_pAddrHead;	 // 현재 노드의 주소를 이전 노드의 next에 저장하기 위함

	if (g_pAddrHead == NULL)	// 한번만 실행됨
	{
		g_pAddrHead = malloc(sizeof(ADDR)); // 머리노드 구조체 할당 --> 할당된 주소가 저장됨

		if (g_pAddrHead == NULL)// 할당 실패
		{
			return 0;
		} 

		g_pAddrHead->next = NULL;	// 일단 null로 저장, 안그러면 쓰레기값
		plocal = g_pAddrHead;	// 할당된 주소 대입
	}
	else
	{
		plocal = malloc(sizeof(ADDR)); // ADDR 구조체 할당 --> 할당된 주소 저장

		if (plocal == NULL) // 메모리 할당 불가
		{
			return 0;
		}

		while (pn->next) // 다음 데이터 존재하면
		{
			pn = pn->next;	// 그 다음 노드 주소를, 마지막 노드 찾기
		}	// null이면 마지막노드

		pn->next = plocal;	// 현재 데이터가 저장되는 노드의 주소를 이전 노드의 next에 저장
		plocal->next = NULL;	// 일단 null값 저장
	}

	strcpy(plocal->name, name);
	strcpy(plocal->tel, tel);
	strcpy(plocal->addr, addr);

	return 1;
}

void print_list(void)
{
	int count = 1;
	ADDR *plist;

	plist = g_pAddrHead;

	while (plist) // 머리 노드부터 ~ 마지막 노드까지
	{
		printf("No. %d\n", count++);
		puts(plist->name);
		puts(plist->tel);
		printf("%s \n\n", plist->addr);

		plist = plist->next;
	}
}

void remove_list(void)
{
	ADDR *plocal;

	while (g_pAddrHead)
	{
		plocal = g_pAddrHead->next; // 다음 노드의 주소

		free(g_pAddrHead); // 현재 노드 메모리 반환

		g_pAddrHead = plocal; // 다음 노드를 현재노드로 옮기기
	}

}

 


Result :

'C' 카테고리의 다른 글

[C] 268 주소록 (아직 작성 안함)  (0) 2021.02.18
[C] 267 이중 링크드 리스트 구현하기  (1) 2021.02.17
[C] 265 큐 구현  (0) 2021.02.17
[C] 264 스택구현  (0) 2021.02.17
[C] 263 야구게임  (1) 2021.02.17

Desc :

 


Source Code :

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

int add(int value);
int delete(int *value);

#define QUEUE_MAX 100

typedef struct tagStack
{
	int array[QUEUE_MAX];
	int front;
	int rear;
}QUEUE;

QUEUE q;

void main()
{
	char buff[100], tmp[100];
	char *op = "+-*/%";
	int index;
	int value1 = 0, value2 = 0;

	q.front = 0;
	q.rear = 0;

	puts("계산식을 1*2처럼 입력하고 엔터키를 치세요.");
	puts("아무것도 입력하지 않으면 계산이 종료됩니다.");

	for (;;)
	{
		printf("계산식: ");
		gets(buff);

		if (strlen(buff) == 0) break; // 무한루프 종료

		memset(tmp, 0, sizeof(tmp));	// tmp버퍼 NULL값으로 채우기 --> atoi함수에서 문자열 끝 확인

		index = strcspn(buff, op);	// 연산자가 있는 위치 반환

		memcpy(tmp, buff, index);	// tmp에 buff를 index 크기만큼 복사

		value1 = atoi(tmp);
		value2 = atoi(&buff[index + 1]);	// index다음부터 문자열을 정수로 변환

		switch (buff[index])
		{
		case'+':
			value1 += value2;
			break;
		case'-':
			value1 -= value2;
			break;
		case'*':
			value1 *= value2;
			break;
		case'/':
			value1 /= value2;
			break;
		case'%':
			value1 %= value2;
			break;
		default:
			puts("잘못된 연산자를 사용하였습니다.");
			continue;
		}

		if (add(value1) == -1)
		{
			puts("더 이상 추가할 수 없습니다.");	// overflow
		}

		printf("%s = %d, q.rear = %d \n\n", buff, value1, q.rear);
	}

	value1 = 0;

	// add종료, 큐에 있는 데이터 꺼내는 무한루프
	for (;;)
	{
		if (delete(&value2) == -1) break;	// 값 꺼내서 value2의 포인터에 저장

		value1 += value2;
	}

	printf("계산의 총합은 %d입니다.\n", value1);
}

int add(int value)
{
	if (q.rear == QUEUE_MAX) return -1;
	q.array[q.rear++] = value;
	return 0;
}

int delete(int *value)
{
	if (q.front == q.rear || q.front == QUEUE_MAX) return -1; // empty 상태
	*value = q.array[q.front++];
	return 0;
}

 


Result :

Desc :

자료를 저장하기 위해 사용되는 알고리즘 중 하나  - 스택

Last-In-First-Out

맨 나중에 저장한 데이터가 가장 먼저 나옴

 

 


Source Code :

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

int push(int value);	// 데이터 삽입
int pop(int *value);	// 데이터 꺼내기

#define STACK_MAX 100	// 스택의 최대 크기

typedef struct tagStack	// 스택 구조체 선언
{
	int array[STACK_MAX];
	int top;
	int bottom;
}STACK;

STACK s;

void main()
{
	char buff[100], tmp[100];
	char *op = "+-*/%";
	int index;
	int value1 = 0, value2 = 0;

	s.top = -1;

	puts("계산식을 1*2처럼 입력하고 엔터키를 치세요.");
	puts("아무것도 입력하지 않으면 계산이 종료됩니다.");

	for (;;)
	{
		printf("계산식: ");
		gets(buff);

		if (strlen(buff) == 0) break; // 종료

		memset(tmp, 0, sizeof(tmp));	// tmp버퍼 NULL값으로 채우기 --> atoi함수에서 문자열 끝 확인

		index = strcspn(buff, op);	// 연산자가 있는 위치 반환

		memcpy(tmp, buff, index);	// tmp에 buff를 index 크기만큼 복사

		value1 = atoi(tmp);
		value2 = atoi(&buff[index + 1]);	// index다음부터 문자열을 정수로 변환

		switch (buff[index])
		{
			case'+': 
				value1 += value2;
				break;
			case'-':
				value1 -= value2;
				break;
			case'*':
				value1 *= value2;
				break;
			case'/':
				value1 /= value2;
				break;
			case'%':
				value1 %= value2;
				break;
			default:
				puts("잘못된 연산자를 사용하였습니다.");
				continue;	
		}

		if (push(value1) == STACK_MAX)
		{
			puts("더 이상 저장할 수 없습니다.");	// overflow
		}

		printf("%s = %d. s.top = %d \n\n", buff, value1, s.top);
	}

	value1 = 0;

	for (;;)
	{
		if (pop(&value2) == -1) break;	// underflow

		value1 += value2;
	}

	printf("계산의 총합은 %d입니다.\n", value1);
}

int push(int value)
{
	if (s.top == STACK_MAX) return -1;	// 삽입 할 수 없음
	s.array[++s.top] = value;
	return 0;
}

int pop(int *value)
{
	if (s.top == -1) return -1; // 꺼낼 값이 없음
	*value = s.array[s.top--];
	return 0;
}

 


Result :

Desc :

 

fflush() --> while (getchar() != '\n'); 변경

 

getchar(): 읽어들인 값을 반환하는 함수

이를 이용해서 줄바꿈 문자 즉, '\n'을 읽어들일 때까지 계속해서 반복하다가 '\n'을 읽어들이면 while문을 빠져나오게 하는 겁니다. 이렇게 하면 위에서 fflush(stdin)를 사용함으로써 원했던 결과와 똑같은 결과를 얻을 수 있습니다.

 

fflush() 함수가 비우는 건 입력 버퍼가 아닌 출력 버퍼입니다. 그런데 위 프로그램에서는 stdin 즉, 표준 입력 스트림을 매개변수로 전달함으로써 입력 버퍼를 비우려고 하고 있습니다.

 

"저렇게 해봤는데 아무 문제 없이 잘 되던데요?"라고 묻는 분이 있을 겁니다. fflush() 함수의 매개변수로 입력 스트림을 전달하는 것은 정의되지 않은 방법입니다. 즉, 어떻게 작동할지 정의돼 있지 않기 때문에 그 누구도 결과를 예측할 수 없고, 경우에 따라 치명적인 결과를 초래할 수도 있습니다. 물론 저렇게 사용하더라도 원하는 방향대로 잘 작동할 수도 있습니다. 하지만 이는 어디까지나 가능성입니다. 

 

출처:https://8ublictip.tistory.com/6

 


Source Code :

#include <stdio.h>
#include <time.h>
#include <stdlib.h>
#include <memory.h>

void clearInputBuffer()
{
	// 입력 버퍼에서 문자를 계속 꺼내고 \n를 꺼내면 반복을 중단
	while (getchar() != '\n');
}

void main()
{
	int com[3] = { 0, };
	int gamer[3] = { 0, };
	int guess[10] = { 0, };
	int count = 0, i = 0;
	int strike = 0, ball = 0;
	int yesno = 0;

	srand(time(NULL));

	puts("야구게임을 시작합니다.");

	while (1)
	{
		com[0] = rand() % 10;
		com[1] = rand() % 10;
		com[2] = rand() % 10;
		count = 1;

		if (com[0] == com[1] || com[0] == com[2] || com[1] == com[2]) continue;

		puts("\n숫자 0~9를 공백으로 분리하여 3개 입력하고 엔터키를 치세요!");

		memset(guess, 0, sizeof(guess));

		while (1)
		{
			strike = 0;
			ball = 0;

			for (i = 0; i < 10; i++)
			{
				printf("%d ", i);
			}
			printf("\n");
			for (i = 0; i < 10; i++)
			{
				printf("%d ", guess[i]);
			}

			printf("\n3개의 숫자[0~9]를 입력하세요:");

			scanf("%d %d %d", &gamer[0], &gamer[1], &gamer[2]);

			if (com[0] == gamer[0]) strike++;
			else if (com[0] == gamer[1] || com[0] == gamer[2]) ball++;

			if (com[1] == gamer[1]) strike++;
			else if (com[1] == gamer[0] || com[1] == gamer[2]) ball++;

			if (com[2] == gamer[2]) strike++;
			else if (com[2] == gamer[0] || com[2] == gamer[1]) ball++;

			if (gamer[0] > 9 || gamer[1] > 9 || gamer[2] > 9)
			{
				puts("입력한 숫자가 너무 큽니다. 0~9를 입력하세요");
				continue;
			}

			guess[gamer[0]] = 1;
			guess[gamer[1]] = 1;
			guess[gamer[2]] = 1;

			printf("[%2d회] %d스트라이크 %d볼 \n\n", count, strike, ball);
			if (strike == 3) break;
			count++;
		}
		
		printf("게임을 계속하시겠습니까?(y/n)>>"); 
	
		clearInputBuffer();

		scanf("%c", &yesno);

		
		if (yesno == 'N' || yesno == 'n')
		{
			break;
		}
	}
}

 


Result :

Desc :

 

확장 시간 구조체 struct _timeb 

tb.millitm ,,,

    기본 시간 구조체 struct tm t


Source Code :

#include <stdio.h>
#include <time.h>
#include <sys/timeb.h>

void main()
{
	struct _timeb tb;
	struct tm t;
	char buff[100];

	_ftime(&tb);

	t = *localtime(&tb.time);

	printf("%4d-%d-%d %d:%d:%d.%d \n",
		t.tm_year+1900, t.tm_mon+1, t.tm_mday, t.tm_hour, t.tm_min, t.tm_sec,tb.millitm);

	printf(ctime(&tb.time));
	printf(asctime(&t));
	puts(_strdate(buff));
	puts(_strtime(buff));
	
	strftime(buff, sizeof(buff), "%Y-%m-%d %H:%M:%S %p(%a)", &t);
	puts(buff);

	strftime(buff, sizeof(buff), "%#Y-%#m-%#d %#H:%#M:%#S %p(%a)", &t);
	puts(buff);

	strftime(buff, sizeof(buff), "%c", &t);
	puts(buff);

	strftime(buff, sizeof(buff), "%x %X", &t);
	puts(buff);

	strftime(buff, sizeof(buff), "%#c", &t);
	puts(buff);

	strftime(buff, sizeof(buff), "%#x", &t);
	puts(buff);

}

 


Result :

Desc :

 

 


Source Code :

#include <stdio.h>
#include <time.h>
#include <stdlib.h>

void main()
{				// 0123456789012345678
	char date[] = "2021-02-09 22:10:20";
	struct tm t = { 0, };

	t.tm_sec = atoi(&date[17]);
	t.tm_min = atoi(&date[14]);
	t.tm_hour = atoi(&date[11]);
	t.tm_mday = atoi(&date[8]);
	t.tm_mon = atoi(&date[5]) - 1;
	t.tm_year = atoi(&date[0])-1900;

	mktime(&t);
	printf("struct tm 변환 후 날짜: %4d-%02d-%02d %02d:%02d:%02d\n",
		t.tm_year+1900,t.tm_mon+1,t.tm_mday,t.tm_hour,t.tm_min,t.tm_sec);
}

 


Result :

+ Recent posts