컴파일 언어 이해하기(3)
함수 포인터
int (*func)(int a); // 자료형 (*함수 포인터 이름)(인자 목록)
#inclde <stdio.h>
int plus(int a, int b) {
return a+b;
}
int main() {
int a=20;
int b=10;
int (*fptr)(int pa, int pb);
fptr = plus;
int result = fptr(a,b); // 간접 참조
printf("결과값: %d\n", result);
return 0;
}
: 함수명 앞에 *만 붙여주면 함수 포인터가 선언된다.
: 함수 포인터도 포인터이므로 주소값을 저장한다.
함수 포인터의 사용 이유 ( 왜 직접 호출 x ?)
: 메모리의 크기 및 위치가 결정되는 시점은 컴파일 타임(정적 바인딩) 또는 런타임 시점(동적 바인딩)
: 비주얼 스튜디오 코드에서 사용되는 extension 들은 플러그인 방식으로 동작
➡️ 새로운 기능을 추가해도 매번 다시 컴파일 해야 하는 불편함이 없음
: 함수 포인터의 사용은 프로그램의 유연한 확장성을 제공
구조체
하나 이상의 서로 다른 종류의 변수들을 묶어서 새로운 데이터 타입을 정의하는 것
구조체 그룹: 정수형, 문자형, 실수형, 포인터, 배열
구조체를 사용하는 이유
연관된 변수들을 하나로 묶어서 관리함으로써 데이터 관리에 유용하다.
데이터 양(변수의 개수)이 많아지면 구조체가 유리하다.
구조체의 기본 형태
struct student {
char name[10]; // 구조체 멤버
int age;
int height;
}
➡️ 구조체 student 는 사용자인 내가 정의한 새로운 데이터 타입이다.
구조체 멤버에 접근하기
[구조체 변수명].[구조체 멤버]
ex) st1.name, st1.age
➡️ 멤버에 접근 시 점(.)을 사용하는데, 이를 직접 접근이라고 한다.
공용체
: 사용자 정의 자료형
: 구조체와 차이점은 메모리 공간을 공유한다는 점이다.
union unTemp {
char a;
int b;
double c;
}
열거형
데이터들을 열거한 집합
enum Week {
sun=0,
mon,
tue,
wed,
thu,
fri,
sat
};
: 열거형의 멤버들은 각 요일을 나타낸다.
: 첫 번째 멤버 sun 을 0으로 설정하면 다음 멤버 mon 은 1씩 증가한다.
동적 메모리 할당
메모리 영역
코드 영역
: 실행할 명령어들이 순서대로 쌓인다. CPU 가 이 영역에서 명령어들을 하나씩 가져다 처리한다.
스택 영역
: 후입 선출 구조, 나중에 들어온 녀석이 먼저 빠져 나간다.
: 지역 변수 및 매개변수 등은 모두 스택 메모리를 사용
힙 영역
: 힙은 컴파일 시가 아닌 실행 시 사용자로부터 할당 메모리를 입력 받음
데이터 영역
: 전역 변수와 static 변수가 저장되는 메모리 영역. 이 메모리는 프로그램 종료 시 소멸
동적 메모리 할당
void * malloc(size_t size);
void* 의 의미 : 타입이 지정되지 않은 포인터 ( 난 당신이 원하는 메모리 크기만큼 할당해줄테니, 메모리는 당신이 원하는 형태로 정해서 사용하세요. )
#include <stdio.h>
{
int num;
int *student;
printf("학생 수를 입력하세요 :");
scanf("%d", &num);
student= (int*)malloc(sizeof(int)*num);
if(student == NULL){
printf("메모리가 할당되지 않았습니다.\n");
return 0;
}
printf("할당된 메모리의 크기는 %d 입니다.\n", sizeof(int)*num);
free(student);
}
객체 지향 프로그래밍
객체 : 영문으로 Object, '사물' 을 나타내는 추상적인 개념
지향: 영문으로 Oriented, '~를 향한다' 는 의미
구조적 프로그래밍 vs 객체 지향 프로그래밍
구조적 프로그래밍
: 순차적, 하향식, 폭포수 방식
: 기능적인 기본 단위는 함수이다.
객체 지향 프로그래밍
: 기능 단위는 객체이다 => 유연하다
: 대표적인 예가 이벤트 기반의 모든 윈도우 프로그램
추상화
추상: 대상에서 특징만을 뽑아낸 것
캡슐화
: 은닉하다, 숨긴다의 의미
: 캡슐화 한다는 것은 외부에서 그 내부를 볼 수 없게 한다는 의미
: 외부로부터 데이터를 조작할 인터페이스가 필요
: 클래스 = 데이터 + 메소드
클래스
: 사전적인 의미로는 '학급'
: 클래스는 사용자 정의 데이터 타입이다 => 추상적인 데이터 타입
: 클래스의 본질은 데이터 타입이라는 점
: 구조체와 비슷, 멤버 변수와 멤버 함수로 구성됨
클래스의 구성
: 사물의 특성을 정리하여 필드와 메소드로 표현하는 과정이 추상화
: 추상화된 결과를 하나의 클래스에 포함시키고 스스로 보호하는 것을 캡슐화
클래스 선언 형식
: 클래스 선언 시 class 키워드를 쓰고, 그 뒤에 클래스 이름을 붙인다.
: 클래스의 요소로는 생성자, 멤버 변수, 메소드 등으로 구성된다.
class Dog {
private int eyes, nose, mouse,ears;
public void bark(){}
}
접근 지정자
- public : 누구나 접근 가능하다.
- protected: 상속 관계에 있을 때 상속 받은 자식 클래스에서 접근이 가능하다. 그 외에는 접근 불가
- internal: 같은 어셈블리(프로젝트) 내의 모든 클래스가 접근 가능하다.
- protected internal: protected 와 internal 의 의미를 모두 포함한다.
- private : 내 클래스 내부에서만 접근 가능하고, 외부에서는 절대 접근할 수 없다.
객체의 선언
: 데이터 타입을 통해 변수를 선언할 수 있다.
: 클래스를 통해 선언한 변수를 객체라고 한다.
Dog a = new Dog();
생성자(constructor)
: 객체도 본질적으로 변수이므로 선언되면 초기화 해야한다.
: 객체 생성시 초기화 전용 메소드를 제공하는데 바로 생성자이다.
: 객체 생성시 자동으로 호출되는 메소드
⚠️ 클래스 이름과 이름이 동일해야 한다, 리턴 타입이 필요없다.
상속성
: 이미 완성된 클래스를 다른 클래스에 상속할 수 있다.
: 부모 클래스로부터 상속을 받을 때 클래스 이름 끝에 콜론(:) , 자바의 경우 extends 를 붙인 후 부모 클래스의 이름을 적는다.
다형성
: 함수의 이름이 같더라도 전달 인자의 타입이나 개수에 따라 구분된다.
: 객체 지향에서는 대표적으로 오버로딩(overloading)과 오버라이딩(overriding) 기법이 있다.
오버로딩
: 사전적 의미 => '과적하다' , '적재하다'
: 겉모습은 똑같지만 내용이 다른 경우
: 이름이 같은 함수일지라도 전달인자 타입이나 개수가 다른 경우
int Plus ( int a, int b) {
return a+b;
}
char Plus ( char a, char b) {
return a+b;
}
오버라이딩
: 사전적 의미 => '위로 올라탄다' , '엎어친다' 는 의미를 갖는다.
: 무언가에 올라타서 기존의 것을 덮어 버린다는 개념
: 상속의 개념이 기반이 되어야한다.
인터페이스
: 메소드의 목록만을 가지고 있는 명세, 사용자 정의 타입
: 메소드의 목록만 선언하고 구현은 하지 않는다.
인터페이스를 사용하는 이유
- 인터페이스는 본체가 정의되지 않는 추상 메소드만 갖는다.
- 인터페이스의 목적은 기존의 기능을 추가하거나 수정의 개념보다는 동일한 개념의 기능을 새롭게 구현하는 기능이다.
- 공동 작업 시 표준을 정하는 역할
public interface IUnit{
void Attack();
void Move();
}
public class Zergling: IUnit {
public void Attack(){ ... }
public void Move(){ ... }
}
메모리 관리
- 플랫폼 기반의 객체 지향 언어는 가비지 컬렉터가 메모리를 자동 관리한다.
- 백그라운드에서 더 이상 사용되지 않는 메모리를 찾아 회수한다.
람다
익명 메소드
- 메소드를 미리 정의하지 않고 사용할 때 정의한다.
- 코드가 간결해진다.
- 별도의 메소드를 만들지 않으므로 코딩 오버헤드를 줄일 수 있다.
- 내용 자체가 복잡하면 안된다.
- 람다식에서 사용된다.
람다식
- 기존 익명 메소드를 더욱 간결하게 만든다.
- 코드를 짧고 간결하게 표현하는 것이 목적이다.
람다식 표현
- (인수) => 표현식 또는 명령문
- (x,y) => x+y 람다식은 "x와 y가 x+y 가 된다 " 로 읽는다.
🌟 배운 점
오늘 드디어 객체 지향 프로그래밍에 대해 배웠다. 이전에 자바를 배워서 오늘 배운 내용을 이해하는 데 큰 어려움은 없었다. 하지만 자바스크립트를 사용하면서 잊고 있던 부분들을 다시 상기하고 복습할 기회가 되었다. 이제 타입스크립트를 배우게 되는데, 자바스크립트와 어떤 점이 다르고, 또 어떤 면에서 더 편리할지 기대가 된다.
'데브코스' 카테고리의 다른 글
타입스크립트(2) (0) | 2024.10.29 |
---|---|
타입스크립트(Typescript) (2) | 2024.10.28 |
컴파일 언어 이해하기(2) (1) | 2024.10.26 |
컴파일 언어 이해하기 (0) | 2024.10.24 |
자바스크립트(2) (3) | 2024.10.23 |