728x90
728x90

01 C++의 역사


C는 데니스 리치가 70년대 초 유닉스 시스템을 개발하기 위해 제작

C++은 미 벨연구소 비얀 스트루스트럽이 80년대 C에 객체 지향 등의 특징을 추가하여 제작
당시 C with class로 발표. 83년 C++로 이름 변경
98년 첫 발표된 ANSI 표준안에 이어 여러 C++ 표준이 있다. ISO, NCITS, ANSI/ISO, X3 등...

 

02 C++의 특징


C는 절차프로그래밍 = 데이터와 명령(함수)을 분리
C++은 객체지향프로그래밍 = 확장성과 재사용성을 고려

C언어를 기본으로 확장한 언어
데이터 추상화를 제공 
객체지향프로그래밍(OOP)를 제공
일반화 프로그램을 지원 : 템플릿 등

 

추상화

더보기

추상화는 객체들의 공통된 특성을 파악하고 불필요한 특성을 제거해서 모델링하는 것으로
유사한 객체들의 덩어리로 공통적 특성을 표현하는 것 
객체지향프로그래밍에서 데이터를 추상화하는 단위는 클래스

 

추상화를 적절히 시키면 코드의 재사용성과 가독성을 높이고 결국 생산성, 에러의 감소와 같은 요소에 영향을 미치게 된다.
 
코딩을 하면서 빈번하게 쓰던 반복문을 살펴보자.
가와 나가 별을 100개 찍는다.
가:
printf("******....100개가 될 때까지 반복");
 
나:
for( i = 0; i < 100; i++ ) { printf("*");}
 
나에서는 *을 찍는 행동을 추상화 시켰다고 볼 수 있다.나에서는 *을 한 번 찍는 다는 것 밖에 행동이 없었지만, 반복문을 사용함으로서 추상화 시켰고 반복문이 실행되며 행동이 실체화 되었다.우리가 자주 쓰던 반복문도 일종의 추상화이다. 이러하듯, 추상화가 마냥 어려운 개념만은 아니다.
https://developers-dev.tistory.com/3

 

 

일반화 프로그램 지원

더보기

일반화 프로그래밍은 데이터를 중시하는 객체 지향 프로그래밍과는 달리 프로그램의 알고리즘에 그 중점을 둔다.

대표적인 C++의 일반화 프로그래밍관련 기능이 템플릿이고

템플릿은 매개변수의 타입에 따라 함수나 클래스를 생성하는 매커니즘이다.
타입이 매개변수에 의해 표현되서 매개변수화 타입이라고도 한다.

데이터타입을 템플릿으로 만드는 것이 대표적
함수 템플릿/클래스 템플릿 등이 있다.

 

절차적 프로그래밍 procedural programming

단계별로 구현한 프로그램
프로시저를 중심으로 설계
함수를 처리하는데 필요한 데이터 (인자)를 전달하고, 함수실행 후 결과값을 반환해서 처리한다
데이터의 배려가 어렵고?
사용된 프로그램을 확장, 재사용하기 어렵다

프로시저 중심에서 데이터 구성중심으로 이동 : 모듈화 프로그램

모듈화 프로그램은 캡슐화가 원칙

 

C++은 모듈성과 엄격한 타입제약을 받는 인터페이스로 유연하다

OOP는 객체의 구성과 객체 간 통신을 정의하는게 중요하다

객체 : 존재하는 것, 생각, 아이디어
클래스 : 객체를 프로그램으로 표현
인스턴스 : 프로그램에서 클래스를 사용해 만든 실제로 실행할 객체

 

객체지향 프로그램 : 객체 단위로 프로그램을 구현

객체지향 프로그램 3대 특성 : 캡슐화, 상속성, 다형성

 

캡슐화  : 객체와 관련된 데이터와 활용하는 함수를 하나로 묶어 놓은 것. 정보 은닉성

클래스 내부 데이터와 함수들을 묶은 것으로 외부에서 접근 불가하다.
객체를 단순화하면서 안전하게 작성할 수 있다.

 

상속성 : 작성된 클래스에 기능을 추가하거나 특정 멤버함수를 수정 등 클래스를 재정의해서 사용하는 것.

기본 클래스(base class)를 상속받는 파생 클래스(derive class)는 기본클래스의 멤버변수와 멤버함수를 모두 상속받고 데이터와 기능을 추가하거나, 특정 멤버 함수를 수정하여 만들어진 새로운 클래스다.

파생클래스를 통해 기본클래스에서 정의한 데이터나 멤버함수에 접근할 수 있다.
기본클래스에서 정의한 멤버함수는 오버라이딩해 수정하거나 새롭게 재정의할 수 있다.
한개의 클래스를 여러개의 클래스에서 기본클래스로 중복 사용할 수 있다.
두 개 이상 기본클래스를 반복하여 상속 받은 것이 다중상속이다.

 

오버라이딩 : 클래스들의 상속 상태에서 기본클래스에 정의된 함수를 파생클래스에서 재정의하는 것

부모의 멤버함수와 원형이 동일해야한다. 부모클래스의 함수는 모두 가려진다. (출처)

 

#include <iostream>

using namespace std;

class A {
	public:
	void over() { cout << "A 클래스의 over 함수 호출!" << endl; }
};

class B : public A {
	public:
	void over() { cout << "B 클래스의 over 함수 호출!" << endl; }
};

int main()
{
	B b;
	b.over();
	return 0;
}

//출처: https://blog.hexabrain.net/175 [끝나지 않는 프로그래밍 일기]

 

다형성 : 상속받을 기본클래스 내부에서 해당함수 이름 앞에 키워드 virtual를 붙여 가상함수로 선언한다.

같은 이름의 함수를 클래스에 따라 객체에 알맞은 행동을 하도록 하는 것.
컴파일러에서 처리, 상속받은 파생클래스 내부에서 해당 클래스가 요구하는 기능을 재정의 후 사용해야 동작된다.

한 클래스 내부에 같은 이름을 가진 멤버함수들을 포함하는 오버로드와
기본클래스와 파생클래스가 같은 이름을 갖는 멤버함수들을 포함하는 오버라이드 방법이 있다.

가상 함수 : 파생클래스에서 재정의할 것을 기대하는 멤버함수로 호출하는 객체의 동적 타입에 따라 실제 호출할 함수가 결정

virtual 멤버함수의 원형;

 

 

 

03 컴퓨터의 데이터 표현과 코드 체계


정보 단위 : 정보를 저장하는 최소단위. 1비트

문자 표현의 기본 단위
1Byte는 8bits. 1바이트는 8비트.

워드(word) :  CPU가 한 번에 처리할 수 있는 데이터의 크기입니다.
하프워드(2바이트) / 풀워드(4바이트) / 더블워드 (8바이트)

CPU에 따라 크기가 결정된다. 

32비트 시스템에서는 32비트 / 8비트 = 4, 즉 4바이트가 1워드(word)로 처리
64비트 시스템에서는 64비트 / 8비트 = 8, 즉 8바이트가 1워드(word)로 처리

필드(field) : data process 자료 처리의 최소 단위
특정 의미를 전달할 수 있는 단위

레코드(record) : 하나 이상의 필드로 구성되는 프로그램 처리의 기본 단위
논리레코드(프로그램 처리 단위)
물리레코드(논리레코드로 구성된 프로그램 입출력의 단위)로 나뉜다.

파일 : 연관성있는 레코드의 집합. 프로그램 구성의 기본 단위

데이터베이스 :  서로 관련된 파일들의 집합

 

수의 표현과 진수

0은 양수를 표현, 1은 음수를 표현한다.
음의 정수 표현은 부호 비트를 사용한 부호화크기 (signed magnitude) 방식|
양의 정수 표현은 unsigned magnitude(부호크기를 표시할 필요가 없다)

최상위 1비트 (MSB: Most Significant Bit)를 부호 표시에 사용, 나머지는 수의 크기를 표시
* LSB: Least Significant Bit 최하위비트

n비트를 사용한 정수는 음/양수 전부 표현 시 -(2의 n-1승)~(2의 n-1승-1) 까지 정수 표현 범위를 갖는다.
범위 초과 시 정상값으로 표현이 안되며 오버플로overflow 라고 한다.

 

1의 보수 complement :  1의 보수는 대부분 산술연산에서 원래 숫자 음수처럼 취급된다
보수 : 보충을 해주는 수. 현재 숫자에서 자릿수가 1단계 올라갈 수 있는 수를 구한다.

00000101 //5
11111010 //-5

2의 보수 : 1의 보수 결과에 1을 더한 것

 

 

04 C++ 프로그램의 개발 단계


C++로 작성한 프로그래믕ㄹ 소스코드(원시코드)라고 하며 파일명.확장자로 저장한다.

test.cpp  //C++프로그램
test.obj  //목적파일
test.exe  //실행파일

 

C++프로그램의 개발 단계 흐름도 

출처 : TCPSCHOOL.com

 

소스 코드 (source code, 원시 코드) : 프로그램을 작성한 코드

소스 파일에 저장되며 텍스트 형식으로 저장한다.

 

컴파일 : 소스코드를 컴퓨터에서 실행할 수 있도록 컴파일러를 사용하여 기계어로 번역

번역된 기계어로 작성된 코드는 목적 코드(object 코드)이며, 목적 파일에 저장된다.
기계어는 연산코드(operation code)피연산자(operand)로 구성된다.

컴파일러는 정확한 C++규칙을 지켜 구문 오류(syntax error)가 없는지 체크한다.
개발자가 실수한 의미상의 오류(semantic error)는 찾지 못한다.

컴파일 시 오류가 발생하면 목적파일이 안만들어진다.

 

링크 : 같은 이름의 여러 식별자가 같은 식별자를 참조하는지를 결정한다.

링커(linker)는 컴파일러가 생성한 목적코드에서 사용하는 표준라이브러리 함수들을 컴파일러 회사가 제공하는 표준라이브러리에서 필요한 코드 모듈을 가져와 목적 코드에 삽입하며 모든 모듈을 조합하며 연결(링크)하여 실행 가능한 실행파일을 생성한다. (윈도우는 exe)

* 요약하면, 여러 분리된 파일들을 컴파일한 각각의 결과물에서 최종적인 실행 파일을 만드는데 필요한 부분들을 찾아 연결하는 작업이다. (https://kldp.org/node/71570

정적 링크 : 필요한 모든 목적코드를 연결해서 완성된 실행파일을 만들어 실행
동적 링크 : 프로그램 실행 중에 프로그램 외부에 존재하는 목적코드를 찾아서 연결 (JAVA는 JVM이 알아서 처리)

프로그램에서 사용한 함수가 없거나 표준라이브러리에 없으면 오류메세지를 띄우고 링크를 중단한다.
오류 발생 시 소스코드에서 수정한다.

링키지 : 링크를 위한 규칙
로더(loader) : 메모리에 할당할 주소를 계산하여 절대 주소 프로그램을 생성한다.

 

 

 

실행 : 컴파일 후 링크까지 성공적이면 컴퓨터에서 실행할 수 있는 파일이 생성된다.

소스코드 작성 시 프로그램 논리가 잘못되면 실행 결과는 목적과 다를 수 있다.
컴퓨터가 다른 원인에 의해 충돌할 수도 있는데 이 경우에도 소스코드를 재검토한다.

 

디버깅 : 오류 발생 시 소스 코드를 단계별로 실행하면서 프로그램에서 사용한 변수들을 조사하는 작업

디버거 : 버그를 잡는다는 뜻

 

 

05 간단한 C++ 프로그램


전처리기 (preprocessor) : #으로 시작하는 문장

 

 

 

06 DEV-C++ 주의사항 (생략 가능)


화면에 결과를 출력하는 창이 순식간에 사라지는 문제 해결
임의의 키를 누를 때까지 창이 계속 열려있는 코드

#include <iostream>

using namespace std;

int main()
{
    cout<<"Hello World";
    cin.get(); // 컴파일, 링크 후 실행키를 누를 때까지 기다림

    return 0;
}

 

 

명령행에서 프로그램 실행하기

모든 C++ 프로그램에는 main함수가 있어야하며 메인함수가 없으면 main 컴파일러에서 오류가 생긴다
소스코드 실행을 시작하는 위치로 특별한 방법으로 정의해서 프로그램을 실행시킬 때 command 라인에서 문자열을 전달해줄 수 있다. 그러면 명령행 인자에 저장되어 프로그램 내에서 사용이 가능하게 된다.

명령행에서 main함수의 원형은 다음과 같다. 

 

main(int argc, char *argv[])
main(int argc, char **argv)

 

argc : 명령행 인자의 개수를 전달받는 정수 타입 매개변수
프로그램 이름을 첫 번째 인자로 사용하기 때문에 하나 이상이어야 한다.

argv : 명령행 인자의 문자열을 저장할 배열 포인터를 매개변수로 전달받아 실행한다.
argv[]의 대괄호 안이 비었으면 배열의 길이가 결정되지 않아 입력한 인자의 개수만큼 처리한다.
argv[0]은 c++ 프로그램명이다.

https://kldp.org/node/48280

artv[argc] 배열은 argc 개수만큼 생성되면서 해당하는 문자열이 저장된다.

 

#include <iostream>

using namespace std;

int main(int argc, char **argv)
{
    for(int i=0; i<argc; i++)
        cout<<"argument " << i << ": " << argv[i] <<endl;   

    return 0;
}

 

웹 컴파일러말고 프로그램에서 돌리면 c: .... .exe 가 나온다.
cmd 창에서 cd 저장한 폴더경로를 입력해 이동한 뒤 프로그램을 실행해본다.

프로그램파일명 + 단어 + 단어등으로 입력한 뒤 실행시키면 빈 칸에 의해 명령과 인자들이 구분되어 출력된다.
프로그램에서 도스 운영체제의 명령은 system() 함수를 사용하여 실행한다.

 

int system(const char *command);
// command : 도스 명령어를 사용하겠음
// 실행 파일의 이름이나 배치 파일 이름을 전달하여 해당 파일 실행

 

아래는 프로그램 내부에서 운영체제의 명령을 직접 실행하는 예제이다.

#include <iostream>

using namespace std;

int main(int argc, char **argv)
{
   system("cls"); //도스 화면 깨끗이 지우기
   system("dir"); // 디렉토리에 있는 파일이나 경로 표시
   system("type c:\\work\\cpp\\hello.cpp"); //파일 내용 표시
   system("pause"); // 임의의 키를 누를 때까지 정지
   // md : 디렉토리(폴더) 생성
   // cd : 디렉토리 변경
   // rd : 디렉토리(폴더) 삭제

    return 0;
}
728x90
728x90
블로그 이미지

coding-restaurant

코딩 맛집에 방문해주셔서 감사합니다.

,

v