(비전공자를 위한) 42서울 라피신에서 C언어로 살아남기

@JHSHIN·2023년 3월 29일
0
post-thumbnail

42서울 선발 과정인 라피신에서 C언어 과제를 수행할 때 필요한 지식을 얻을 수 있는 방법을 소개하는 글입니다. 과제에 대한 정답 코드나, 과제의 상세한 정보는 기밀 사항으로서 이 글에 포함되지 않습니다.

1. 42 헤더를 넣어보자!

1-1 42헤더란?

.c로 끝나는 소스 코드에 포함해야하고, 작성자와 생성일, 수정일이 예쁘게 적힌 주석을 의미한다.

없어도 프로그램 실행에는 전혀 문제가 없지만, 42서울에 대한 소속감과 애정이 생긴다고 한다.

1-2 헤더를 넣을 수 있도록 준비해보자!

  1. git clone https://github.com/42Paris/42header → 42 헤더 파일을 깃에서 가져옴
  2. mv ./42header/plugin ~/.vim → 오류가 난다면 ~/.vim 폴더가 없는 것이므로 mkdir ~/.vim 후 다시 해보자
  3. ~/.zshrcexport MAIL=$USER@student.42seoul.kr 을 추가하기

1-3 이제 헤더를 넣어보자!

Shell 과제가 끝난 당신은 앞으로 이제 소스코드에 "42헤더"를 넣어야 한다.

헤더를 넣을 때 vim의 명령 모드에서 :Stdheader 를 입력하지 않고 F1 키만 눌러도 잘 된다.
안되면 저주받은 맥이니까 그냥 :Stdheader를 치자.

BONUS)

헤더는 대충 이렇게 생겼다!


2. 헤더파일은 뭐야?

2-1 헤더파일이란?

.h로 끝나는 헤더파일에는 다양한 함수가 이미 구현되어 있어서, 이미 C언어에서 만들어놓은 헤더파일을 불러온다면 우리가 함수를 직접 구현을 하지 않고 사용할 수 있게 해준다.

헤더파일에는 여러가지(unistd.h, stdio.h, stdlib.h, math.h 등등)가 있다.

참고로 여기서의 헤더파일이랑 앞서의 42헤더랑은 관련이 하나도 없다. 이름만 비슷하다.

unistd.h 헤더에는 이것들을 포함해서 더 많은 함수들이 정의되어 있다. 외울 필요는 하나도 없다. (가장 밑에 write 함수가 정의되어 있는 것이 뭔가 낯익을 것이다!)

2-2 알았으니까 이제 필요한 함수를 가져오자!

만약, 문제에서 사용할 수 있는 함수를 write라고 정해주면, 구글링을 통해 write가 어느 헤더파일에 내장되어 있는지를 확인하고,

#include <필요한 헤더파일.h> 를 42헤더 바로 밑에 적어서 컴파일러에게 내가 필요한 함수가 들어있는 헤더파일을 불러오라고 명령해야 한다. 아까 봤듯 write는 <unistd.h>에 있다.

그럼 이제 내가 사용해야 하는 함수를 호출할 수 있다!

2-3 그래서 write 함수를 불러오긴 했는데 어떻게 써야하는걸까?

구글링을 통해 write 함수의 반환형과 인자, 기능 등을 공부하자! 스스로 학습하고, 그래도 모르면 옆의 동료가 친절하게 알려줄 것이다!


3. 알겠는데, 나는 C언어를 모른다니까요?

함수를 구현해야 한다면, 우선 #include <~.h> 의 함수를 선언해야 한다.

함수는 다음과 같이 선언한다.

반환자료형 함수이름(인자) {구현 내용;}

반환자료형은 말 그대로 return 하는 값의 자료형을 의미하고, 함수 이름은 함수를 호출하기 위한 이름을 의미한다. 인자는 함수를 호출시 외부에서 받아와서 함수 내부에서 사용할 값을 의미한다.

인자를 왜 넣을까? 우리가 자판기를 이용할 때 1. 돈을 넣고 2. 버튼을 누른다. 얼마를 넣었고, 어떤 버튼을 눌렀는지 그 정보를 자판기 함수를 호출하면서 함께 보내주어야만 자판기가 작동할 수 있게 된다. 그래서 자판기는 둘 중 하나의 인자라도 빠지면 작동이 불가능하다.

왜 코드의 끝에 세미콜론을 적어야 하는가? 세미콜론은 현재 문장이 끝났고 다음에 나오는 문장은 새 문장임을 알려준다. C에서 세미콜론을 사용하면 코드를 볼 때 애매함과 혼란을 방지할 수 있다. 세미콜론을 적지 않으면 어디까지가 한 문장인지 컴파일러는 모르기 때문에 컴파일이 안된다.

이제 당신은 함수를 구현할 수 있다.


4. 함수를 구현하세요 vs 프로그램을 구현하세요.

문제에는 대개 1. 함수를 구현하라는 문제와 2. 프로그램을 만들라는 문제 이렇게 두 부류가 있다.

함수를 구현하는 문제는 소스 코드(.c 파일)에 함수만 구현하면 된다. 간단하다고 생각할 수 있지만, 테스트하기가 어렵다. 왜냐면 실행이 안되기 때문이다.

왜 실행이 안될까? C언어는 컴파일러가 먼저 main() 함수를 찾아 실행시킨다. 소스 파일 내에 main() 함수가 없으면 컴파일시 오류가 발생한다. (그래서 코딩을 처음 배울 때 int main(void)를 가장 먼저 쓰라고 배웠을 것이다.)

프로그램을 만드는 문제는 소스 파일 내에 main() 함수를 포함하여 실행이 될 수 있도록 만드는 문제기 때문에 제대로 잘 작동하는지 안되는지 테스트하기가 수월한 편이다.

그래서 함수를 구현하는 문제는 cp 명령어로 다 작성한 소스 파일을 하나 복사하여 더 만들어놓고, 복사한 파일에 main() 함수를 만들고, main() 함수의 내부에서는 문제에서 구현하라고 시켰던 함수를 테스트하는 코드를 넣는다. 그리고 컴파일시켜 실행해본다.

제출할 때는 .c 소스 파일만 제출해야 한다.


5. Norminette는 뭐지? 왜 하는거지?

만약 수백명의 개발자가 하나의 프로그램을 두고 협업을 한다고 가정해보자.

각각의 개발자는 코딩 스타일이 모두 다를 것이고, 따라서 그들이 작성한 코드는 비록 잘 실행이 된다고 하더라도 문장들이 깔끔하지 못하고 뒤죽박죽 제멋대로여서 알아보기가 너무나도 어려울 것이다.

따라서 코드를 작성하는 스타일을 규칙으로 정해놓는 편이 유지보수에 유리하다.

그래서 우리는 42 커뮤니티에 들어왔으니, 어쨌든 42만의 코드 스타일로 코딩을 해야 하는 것이다. (로마에 가면 로마법~~~블라블라)

42의 코드 스타일을 norminette라고 부르고, 그 규칙을 반드시 지켜야 한다.

쉘에서(터미널에서) 현재 폴더에 내가 작성해놓은 .c의 소스 파일이 있다면 norminette 라고 입력해보자. 당신의 소스 코드가 42에서 정한 규칙에 맞는지 검사를 해줄 것이다.

불친절한 42의 교육 방식 속에서 가장 친절한 친구가 얘다. 어느 줄에서 어느 부분이 틀렸는지 싹 다 알려준다.

5-2 중요한 규칙들

int main(void); ← 함수 작성시 반환자료형과 이름 사이는 탭(tab)으로 띄어야 한다.

char c; ← 변수 선언시에도 탭으로 띄며, 선언과 초기화(변수에 초기값을 지정해주는 것)를 동시에 하지 않는다.

c = ‘a’; ← 변수 선언이 모두 끝나면, ‘한 줄’을 띄고(= Enter를 두번치고) 변수 초기화를 해준다.

while (c <= ‘65’) ← 연산자(<, > 등) 앞뒤로 한 칸을 띄고, while 뒤에 조건을 넣기 전에 한 칸 띈다.

변수 선언과 초기화 사이의 한 줄의 개행을 제외하고, 빈 줄이 있으면 안된다.

main() 함수는 반환자료형을 int로 하고 return 0; 로 끝내야 한다. 프로그램을 원래 상태로 돌려놓는다는 의미.


6. 소스 파일을 바로 실행시킬 수 있나요?

소스 코드는 인간의 언어(C언어)로 작성되었기 때문에, 컴퓨터가 바로 알아들을 수 없다.

소스 코드를 컴퓨터가 알아듣는 언어로 통역해주는 통역가를 ‘컴파일러’라고 부르기로 했다.

우리가 쓸 컴파일러는 cc라는 컴파일러다. 컴파일러는 또 아무튼 여러 종류가 있다.

폴더 내에 소스 코드가 있다면, cc -Wall -Wextra -Werror 소스코드.c 를 입력하면 곧 컴파일된 파일이 폴더 내에 생긴다. -Wall -Wextra -Werror 옵션을 주지 않아도 컴파일이 되지만, 라피신의 채점기계는 저 옵션을 주고 컴파일한다고 하니 우리도 그렇게 해서 오류를 방지하자.

이제 ls 명령어로 컴파일된 파일을 확인할 수 있다.

그 파일의 이름은 a.out 으로 나온다. 따라서 ./a.out 을 입력하면 프로그램이 실행이 된다.

cc -o 원하는이름 소스코드.c → 이처럼 -o라는 옵션은 원하는 이름으로 실행파일을 만들 수 있게 해준다.


7. 학습에 도움이 될만한 자료들

자료형이란?

자료형이 뭔가요 교수님!

포인터란?

C는 포인터가 어렵다던데 (그렇지 않아요. 겁먹지 마세요!)

함수란?

자판기에 동전을 넣고 버튼을 눌렀더니 “””알 수 없는 과정”””을 거쳐서 음료가 나왔다는것? 함수는 내부적으로 어떻게 구현이 되었는지는 몰라도 그저 함수의 기능만 알면 사용할 수 있다.


8. 일반적으로 알고리즘을 짜는 방법

문제를 보고 바로 vim으로 C언어를 작성하는건 천재다. 미술로 치면 피카소 급?

우리는 평범하니까 미리 스케치를 해보고, 그 위에 색칠을 해서 예쁜 그림을 완성시키는 걸로 하자.

스케치하는 방법은 여러 가지가 있는데, 일단 몇가지 소개해드리려 한다.

위를 순서도라고 부른다.

미리 논리의 흐름을 적어보면서 어떤 식으로 함수를 구현해야 할지 생각을 정리해볼 수 있다.

이것은 의사코드(수도코드)라고 부른다.

함수가 작동하는 방식을 프로그래밍 언어의 형식과 비슷하게 적어보는 것이다.

정해진 방법은 없으므로 그냥 종이와 펜으로 생각을 정리한 뒤(어떤 자료형을 써야 하는지, 반복문을 어떻게 쓸 것인지, 예외는 없는지 등), 그것을 C문법에 맞게 작성하면 된다.

profile
We Need Better UX

0개의 댓글