From 3b2b5f993a39d7aa526f9b3644464ddd2bbe0b29 Mon Sep 17 00:00:00 2001 From: hajiiiin <101108440+hajiiiin@users.noreply.github.com> Date: Wed, 2 Nov 2022 23:25:07 +0900 Subject: [PATCH 1/6] Create 1week.md --- 1week.md | 147 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 147 insertions(+) create mode 100644 1week.md diff --git a/1week.md b/1week.md new file mode 100644 index 0000000..482613f --- /dev/null +++ b/1week.md @@ -0,0 +1,147 @@ +# CH 1~9 + +**프로그래밍 언어**란 + +- 사람과 컴파일러가 이해할 수 있는 형태의 언어 + +**컴파일러** + +- 프로그래밍 언어를 기계어로 번역 + +**기계어** + +- 0과 1로 구성된 형태의 언어 + +## c언어의 장점 + +- 절차지향적 +- 이식성이 좋다 (cpu에 따라 재작성할 필요가 없다.) +- 좋은 성능 : 메모리 용량이 적고 속도 저하도 최소화할 수 있다. + +## c언어 흐름 + +1. 프로그램 작성 +2. 컴파일 (compile) +3. 링크 (link) +4. 실행파일 생성 (.exe) + +### 기본 툴 + +```c +int main(void) { + return 0; +} //아무것도 안하는 코드, 반환 0 +``` + +### 연산자 + +```c +int num = 1; + +printf(++num); //2 출력 +printf(num++); //2 출력 하고 num은 +1됨 (후위 연산) +printf(num); //3 출력 +``` + +### 명시적 형 변환 : 강제로 형 변환 시킴 + +```c +double num1 = 5.14 + 9; // int 9를 double형 9.0으로 변환해서 계산함 +``` + +### printf 함수 + +“”로 묶어줌 , 문자열 중간에 따옴표를 넣고 싶다면 + +1️⃣ \” 사용 + +2️⃣ “큰 따옴표로 묶었다면 ‘ 사용, ‘작은 따옴표로 묶었다면 “사용 + +```c +printf("%d", 변수명); //정수형 출력 +printf("%c", 변수명); //문자형 출력 + +//아스키 코드 +printf("%d %c", 'A', 65); //'A'의 정수형 65 출력, 65의 문자형 A 출력 +``` + +- 필드 폭 지정하여 출력하기 + + %8d : 필드 폭을 8로 확보하고, 오른쪽 정렬해서 출력 + + %-8d : 필드 폭을 8로 확보하고, 왼쪽 정렬 출력 + +- %s : 문자열 입출력에 사용 + +### 반복문 + +- **while** + - 중첩 반복 + - while조건이 참일 때 실행 + + ```c + //구구단 출력 반복문 + + int main(void) { + int cur = 2; + int is = 0; + + while(cur<10) { + is = 1; + while(is<10) { + printf("%d X %d = %d", cur, is, cur*is); + } + cur++; + } + return 0; + } + ``` + +- **do-while** + - 일단 실행 후 조건 비교 =⇒ 적어도 1번은 실행됨 + + ```c + do { + printf("heelo world! \n"); + num++; + } while(num<3); + ``` + +- **for** + - for(변수 초기식; 조건식; 증감식){} 으로 구성 + + ```c + for(int num=0; num<3; num++) { + printf("hi~"); + } + ``` + + +```c +//구구단 출력 +int main(void) { + int cur, is; + + for(cur=2; cur<10; cur++) { + for(is=1; is<10; is++) { + printf("%d X %d = %d \n" , cur, is, cur*is); + } + printf("\n"); + } + return 0; +} +``` + +2 X 1 = 2 (여기 한 줄 띄는 게 두번째 for문의 \n) + +2 X 2 = 4 + +‘’’ + +(여기가 첫번째 for문의 printf(”\n”); + +3X1=3 + +‘’’ + +이렇게 출력됨 From e141d3366d43cdafbcae30e217a8843c21bb5d7e Mon Sep 17 00:00:00 2001 From: hajiiiin <101108440+hajiiiin@users.noreply.github.com> Date: Sun, 6 Nov 2022 19:35:25 +0900 Subject: [PATCH 2/6] Update 1week.md --- 1week.md | 45 +++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/1week.md b/1week.md index 482613f..a1bbcff 100644 --- a/1week.md +++ b/1week.md @@ -145,3 +145,48 @@ int main(void) { ‘’’ 이렇게 출력됨 + +### 조건문 + +- 삼항 연산자 + - 조건식 ? 참일 때 : 거짓일 때 + +### switch문 + +case에 break; 있으면 그 case만 실행 + +case에 break; 없으면 그 case부터 이후 case 쭉 실행 + +### goto + +rabbit : 위치를 표시 + +goto rabbit : rabbit으로 무조건 이동 + +```c +goto ONE; + +ONE: + printf("1"); + goto END; +END: + return 0; +``` +switch문과 비슷하게 생김 + +### 함수선언 +```c +int Increment(int n); //함수 선언 + +int main(void) { + int num=2; + num = Increment(num); + return 0; +} + +int Increment(int n) { // 함수 + n++; + return n; +} +``` +함수가 불려진 것 보다 뒤에 있으므로 실행이 안됨 그러므로, 이름을 한번 불러주어 함수를 호출 할 수 있도록 해줌 From e2027b483539db8298f3686c48dcaa48ec0d96a3 Mon Sep 17 00:00:00 2001 From: hajiiiin <101108440+hajiiiin@users.noreply.github.com> Date: Thu, 10 Nov 2022 14:40:35 +0900 Subject: [PATCH 3/6] Create 2 week --- 2 week | 114 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 114 insertions(+) create mode 100644 2 week diff --git a/2 week b/2 week new file mode 100644 index 0000000..09d525e --- /dev/null +++ b/2 week @@ -0,0 +1,114 @@ +# Ch 12-15 포인터 + +--- + +### 포인터 변수 + +: 주소 값을 저장하기 위해 사용되는 변수 + +- 선언 + +```c +int num = 7; +int *pnum; //포인터 변수 pnum 선언 +pnum = # //num의 주소값을 포인터 변수에 대입 +``` + +```c +int *punm1; //int형 변수를 가리키는 포인터 +double *pnum2; //double형 변수를 가리키는 포인터 + +type *pnum3; //으로 선언할 수 있다 +``` + +```c +pnum = # +pnum = 30; //하면 num의 주소값이 바뀜 +*pnum += 30; //하면 num + 30됨 +``` + +- ⭐ `*pnum == num` + +### 포인터 배열 + +```c +int main(void) { + int arr1[3] = {1, 2, 3}; + double arr2[3] = {1.1, 2.2, 3.3}; + + printf("%d %g \n", *arr1, *arr2); //1 1.1 출력 + *arr1 += 100; + *arr2 += 100; + printf("%d %g \n", *arr1, *arr2); //100 100.1 출력 + return 0 ; +} +``` + +- `*배열명` 하면 배열[0]의 값을 불러옴 ⬇️ 밑의 코드 참고 +- 인덱스 0 말고 다른 인덱스를 부르고 싶다면? ⭐ `arr[i] == *(arr + i)` + +```c +int arr[3] = [1, 2, 3}; +int *ptr = &arr[0]; // int *ptr = arr; 와 같은 의미 + +printf("%d %d %d", *ptr, *(ptr+1), *(ptr+2)); // 1 2 3 순서대로 출력 +``` + +- ptr (포인터 배열)로 arr (배열)을 부를 수 있음 + +```c +int arr[3] = [1, 2, 3}; +int *ptr = &arr[0]; // int *ptr = arr; 와 같은 의미 + +printf("%d %d", ptr[0], arr[0]); //1 1 출력 +``` + +### 포인터로 문자열 표현 + +❓ str1[ ]과 *str2가 각각 어디에 저장되는 거지? + +```c +char str1[] = "My String!"; //배열이 생성됨 +char *str2 = "Your String"; //❓ +``` + +```c +#include + +int main(void) { + char str1[] = "My String"; //변수 형태의 문자열 + char *str2 = "Your String"; //상수 형태의 문자열 + printf("%s %s \n", str1, str2); + + str2 = "Our String"; //str2의 값 변경 + printf("%s %s \n", str1, str2); + + str1[0] = 'X'; //str1의 인덱스 0 값 바꾸기 + //str2[0] = 'X'; 문자열 변경 실패! 상수 성향의 문자열이라 값변경 안됨 (그래서 주석처리함) 주석 뺴면 오류 + printf("%s %s \n", str1, str2); + return 0; +} +``` + +![출력 결과](https://s3-us-west-2.amazonaws.com/secure.notion-static.com/2daf9fa9-0001-474e-8e31-5f9671277a68/Untitled.png) + +출력 결과 + +### 인자 전달 + +- C언어에서는 배열 타입을 매개변수로 보낼 수 없음 ⇒ 배열 포인터를 보낸다! + +```c +int main(void) { + int arr[3] = {1, 2, 3}; + + SimpleFunc(arr); +} + +void SimpleFunc(int * param) { //int param[]과 같은 의미 + printf("%d %d \n", param[0], param[1]); //포인터 변수를 이용해서 + //배열의 형태로 접급 가능 +} +``` + +단, int *ptr = arr; 대신 int ptr[ ] = arr; 는 불가능 From b5be85ce2791cd7a5321f50ca42946a4f89115eb Mon Sep 17 00:00:00 2001 From: hajiiiin <101108440+hajiiiin@users.noreply.github.com> Date: Thu, 10 Nov 2022 14:41:29 +0900 Subject: [PATCH 4/6] Rename 2 week to 2 week.md MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 형식 변경 --- 2 week => 2 week.md | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename 2 week => 2 week.md (100%) diff --git a/2 week b/2 week.md similarity index 100% rename from 2 week rename to 2 week.md From 7ab3c3c50165c7f3129be7a187211bdc275cd670 Mon Sep 17 00:00:00 2001 From: hajiiiin <101108440+hajiiiin@users.noreply.github.com> Date: Thu, 10 Nov 2022 15:11:55 +0900 Subject: [PATCH 5/6] Update 2 week.md --- 2 week.md | 81 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 81 insertions(+) diff --git a/2 week.md b/2 week.md index 09d525e..e9a3096 100644 --- a/2 week.md +++ b/2 week.md @@ -112,3 +112,84 @@ void SimpleFunc(int * param) { //int param[]과 같은 의미 ``` 단, int *ptr = arr; 대신 int ptr[ ] = arr; 는 불가능 + +### call-by-value + +: `값`을 전달하는 형태의 함수 호출 + +```c +void Swap(int n1, int n2) { + int temp = n1; + n1 = n2; + n2 = temp; + printf("n1 n2: %d %d \n", n1, n2); +} + +int main(void) { + int num1=10; + int num2=20; + printf("num1 num2 : %d %d \n", num1, num2); //10 20출력 + + Swap(num1, num2); // 20 10 출력 + printf("num1 num2 : %d %d \n", num1, num2); // 10 20 출력 + + return 0; +} +``` + +Swap을 해줘서 num1, num2의 값도 바뀌길 원했지만 main에는 영향을 주지 않음 (함수 내에서의 결과는 외부에 영향X) + +### call-by-reference + +: `주소`를 전달하는 형태의 함수 호출 + +```c +void Swap(int *ptr1, int *ptr2) { + int temp = *ptr1; + *ptr1 = *ptr2; + *ptr2 = temp; + printf("n1 n2: %d %d \n", n1, n2); +} +int main(void) { + int num1=10; + int num2=20; + printf("num1 num2 : %d %d \n", num1, num2); // 10 20 + + Swap(num1, num2); // 20 10 + printf("num1 num2 : %d %d \n", num1, num2); // 20 10 + + return 0; +} +``` + +swap 함수 내에서의 *ptr1은 main 함수의 num1 + +매개변수 int *ptr1 = 입력받은 값 num1 + +그러므로 int *ptr1 = num1 + +⇒ 외부의 변수 값 변함 + +- scanf 함수 호출 시 & 연산자를 붙이는 이유 + - scanf 함수가 외부에서 선언된 변수에 접근하려면 주소값을 알아야함 (call-by-reference) + - str은 배열의 이름이고 자체가 주소값임 [참고](https://www.notion.so/Ch-12-15-c9b4827127ae4265898885424b9b7fae) = &연산자 안붙임 + +### const 선언 + +: 값 변경 X ⇒ 안정성 높아짐 + +```c +const int * ptr = # +``` + +- 포인터 변수 ptr을 이용하여 ptr이 가리키는 변수인 num의 값을 변경하는 것 허용X + - num 자체의 값 변경X가 아닌 ptr을 이용하여 바꾸는 것이 불가능 + +```c +int *const ptr = &num1; +``` + +- 포인터 변수 ptr에 저장된 값을 상수화하겠다. + - num의 값 변경 X + +🔼 두개 동시에 선언 가능 From e4e86736b87ab7731bfbb5ce9dbc5677f3b76d7b Mon Sep 17 00:00:00 2001 From: hajiiiin <101108440+hajiiiin@users.noreply.github.com> Date: Wed, 23 Nov 2022 22:24:48 +0900 Subject: [PATCH 6/6] Create 4 week.md --- 4 week.md | 128 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 128 insertions(+) create mode 100644 4 week.md diff --git a/4 week.md b/4 week.md new file mode 100644 index 0000000..0fec3cd --- /dev/null +++ b/4 week.md @@ -0,0 +1,128 @@ +# CH 16-19 + +## 다차원 배열 + +- 2차원 배열의 선언 + +```c +type형 배열명[세로길이][가로길이]; +``` + +- 2차원 배열 선언과 동시에 초기화하기 + +```c +int arr[3][3] = {{1,2,3},{4,5,6},{7}}; + +//출력 +1 2 3 +4 5 6 +7 0 0 //자동으로 0이 채워짐 + +int arr[3][3] = { 1,2,3,4,5,6,7,8 }; + +//출력 +1 2 3 +4 5 6 +7 8 0 +//별도의 중괄호를 사용하지 않으면 좌 상단부터 차례대로 초기화가 됨 +``` + +- 배열 크기 생략 + +```c +int arr[][] = { 1,2,3,4,5 }; //오류!! 채워넣지 못함 + +int arr[][2] = {1,2,3,4,5,6}; //세로길이 생략 가능 3으로 계산해줌 +``` + +## 포인터의 포인터 + +### 이중 포인터 변수 + +```c +int main(void) { + double num = 3.14; + double *ptr = # + double **dptr = &ptr; + double *ptr2; + + printf("%9g %9g \n", ptr, *dptr); + printf("%9g %9g \n", num, **dptr); + ptr2 = *dptr; //==> ptr2 = ptr과 같은 말 + *ptr2 = 10.99 + printf("%9g %9g \n", num, **dptr); + + return 0; +} +``` + +(출력) + +num주소값 num주소값 + +3.14 3.14 + +10.99 10.99 + +즉, ptr == *dptr / num == **dptr / *ptr2 == **dptr 임을 알 수 있다. + +### 포인터 변수의 Swap + +```c +#include +#define _CRT_SECURE_NO_WARNINGS +#pragma warning(disable:4996) + +void SwapIntPtr(int* p1, int *p2) { + int* temp = p1; + p1 = p2; + p2 = temp; +} + +int main(void) { + int num1 = 10 , num2 = 20; + int* ptr1, * ptr2; + ptr1 = &num1, ptr2 = &num2; + printf("*ptr1, *ptr2: %d %d \n", *ptr1, *ptr2); + + SwapIntPtr(ptr1, ptr2); + printf("*ptr1, *ptr2: %d %d \n", *ptr1, *ptr2); + + return 0; +} +``` + +### 삼중 포인터 + +```c +int ***ptr; //이중 포인터 변수의 주소를 담는 용도 +``` + +### 포인터의 필요성 + +- scanf함수와 같이 함수 내에서 함수 외부에 선언된 변수의 접근을 허용하기 위해 +- 메모리의 동적 할당 등등 +- 자료구조를 공부하게 되면 보다 넓게 필요성을 이해할 수 있음 + +### 2차원 배열이름의 포인터 + +- 형 결정 짓기 + + ```c + char (*arr1)[4]; //char형 변수를 가리키면서, 포인터 연산 시 sizeof(char)x4의 크기 단위로 증가 및 감소하는 포인터 변수 + double (*arr2)[7];//double형 변수를 가리키면서, 포인터 연산 시 sizeof(double)x7의 크기 단위로 증가 및 감소하는 포인터 변수 + ``` + + +### 배열 포인터 vs 포인터 배열 + +```c +int (*whoA)[4]; //배열 포인터 : 배열을 가리킬 수 있는 포인터 +int *whoB[4]; //포인터 배열 : 포인터 변수로 이루어진 배열 +``` + ++ +``` +arr[i] == *(arr + 1) //같은 의미 +*arr == arr[] //같은 의미 +```