C++ 14주차 템플릿 라이브러리
Map
특징
- (‘키’, ‘값’)의 쌍을 원소로 저장하는 제네릭 컨테이너
- 동일한 ‘키’를 가진 데이터를 중복 저장할 경우 오류 발생
- 많은 응용에서 필요
- 사용을 위해서는 ‘#include<map>‘ 선언 필요
함수
| 함수 | 내용 |
|---|---|
| insert(pair<> *element) | 키와 값으로 구성된 pair 객체 삽입 |
| at(key_type& key) | 키에 해당하는 값 반환 |
| begin() | 첫번째 pair 객체에 대한 참조 반환 |
| end() | map의 끝을 가르키는 참조 반환 |
| empty() | map이 비어있을 경우 true |
| find(key_type& key) | 키 값에 해당되는 원소를 가르키는 iterator 반환 |
| erase(key_type& key) | iterator가 가르키는 원소 삭제 |
| size() | map의 데이터 개수 반환 |
| operator[key_size& key] () | 키에 해당되는 값을 반환 |
| operator=() | 이 map을 다른 map에 복사 |
예시
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
int main()
{
map<string, string> dic;
dic.insert(make_pair("love", "사랑"));
dic.insert(make_pair("apple", "사과"));
dic["cherrry"] = "체리"; //("cherry", "체리") 저장
cout << "사전의 단어 수 : " << dic.size() << endl;
string eng;
while (true)
{
cout << "찾고 싶은 단어 :";
getline(cin, eng); //사용자로부터 단어 입력
if (eng == "exit")
break;
if (dic.find(eng) == dic.end()) //해당 키가 존재 X할 경우
cout << "값 존재 X" << endl;
else
cout << dic[eng] << endl;
}
cout << "종료" << endl;
}
Output
1
2
3
4
5
6
7
사전의 단어 수 : 3
찾고 싶은 단어 :apple
사과
찾고 싶은 단어 :ex
값 존재 X
찾고 싶은 단어 :exit
종료
STL 알고리즘
알고리즘 함수
템플릿 함수
전역함수
- STL 컨테이너의 클래스의 멤버함수가 X
- iterator와 함께 작동
C++ 표준 템플릿 라이브러리
종류 함수 계수 알고리즘 count 탐색 알고리즘 search, find 비교 알고리즘 equal, mismatch 초기화 알고리즘 fill, generate 변경 알고리즘 transform 복사 알고리즘 copy 삭제 알고리즘 remove, unique 대치 알고리즘 replace 정렬 알고리즘 sort 분할 알고리즘 partition sort() 함수 사례
2개의 매개 변수
1번째 매개 변수 : 정렬을 시작한 원소의 주소
2번째 매개 변수 : 정렬 범위의 마지막 원소 다음 주소
3번째 매개 변수 : 오름차순, 내림차순, 사용자 정의(생략 가능)
1 2 3 4
vector<string> vec; ... sort(v.begin(), v.begin()+3) //v.begin() - v.begin()+2까지, 처음 3개 원소 정렬
예제
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
int main() { //STL 알고리즘 sort()의 예제 vector<int> v; //정수 벡터 생성 cout << "5개의 정수 입력하세요 : "; for (int i = 0; i < 5; i++) { int n; cin >> n; v.push_back(n); //키보드에 읽은 정수를 벡터에 삽입 } //v.begin() - v.end() 사이의 값을 오름차순으로 정렬 //sort() 함수의 실행결과 : 벡터 v의 원소 순서 변경 sort(v.begin(), v.end()); vector<int>::iterator it; //벡터 내 원소를 탐색하는 iterator 변수 선언 for (it = v.begin(); it != v.end(); it++) cout << *it << ' '; cout << endl; }
Output
1 2 3 4 5 6
5개의 정수 입력하세요 : 56 23 65 75 85 23 56 65 75 85
auto를 이용한 변수 선언
정의
- 컴파일러에서 변수의 타입을 추측해 자동으로 선언 함
선언
1
auto 변수명 = 데이터값;
- auto a = 1.23; //double 타입으로 선언
- auto b = 123; //Int 타입으로 선언
- auto c = &b; //int 주소를 저장하는 int 타입으로 선언
참조형 타입으로 선언 예시
1 2 3
int n = 10; int& ref = n; auto d = ref; //d는 int& 타입
리턴 타입으로 선언 예시
1 2
int square(int x) { return x*x; } auto ret = square(3); //ret는 int타입
vector
iterator 타입으로 선언 1 2
for(auto iter = vec.begin(); iter != vec.end(); iter++) cout << *iter << endl;
예시
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
int square(int x) { return x * x; } int main() { //auto 이용한 변수 선언 auto c = 'a'; //char 타입 auto pi = 3.14; //double 타입 auto one = 1; //int auto* p = &one; //int* 타입 cout << c << " " << pi << " " << one << " " << *p << endl; //함수의 리턴 타입으로 추론 auto ret = square(3); //square()의 리턴타입이 int이므로 int cout << *p << " " << ret << endl; vector<int> vec = { 1,2,3,4,5 }; //벡터 vec에 5개 원소 1,2,3,4,5 삽입 vector<int>::iterator iter; for (iter = vec.begin(); iter != vec.end(); iter++) cout << *iter << " "; //1 2 3 4 5 출력 cout << endl; //템플릿에 auto를 사용해 간소화 for (auto iter = vec.begin(); iter != vec.end(); iter++) cout << *iter << " "; //1 2 3 4 5 출력 }
Output
1 2 3 4
a 3.14 1 1 1 9 1 2 3 4 5 1 2 3 4 5
Stream
- 데이터의 흐름
- 데이터를 전송하는 소프트웨어 모듈
- 스트림의 양 끝에는 프로그램과 장치 연결
- 보낸 순서대로 데이터 전달
- 입출력 기본 단위 : Byte
종류
- 입력 스트림
- 입력장치, 네트워크, 파일로부터 데이터를 프로그램으로 전달하는 스트림
- 출력 스트림
- 프로그램에서 출력되는 데이터를 출력장치, 네트워크, 파일로 전달하는 스트림
입출력 스트림
C++ 표준에서는 스트림 방식만 지원함
C++ 표준에서의 스트림은 버퍼를 가짐
입력 스트림의 버퍼
- 목적 :
- 입력 장치로부터 입력된 데이터를 프로그램으로 전달 전, 일시 저장
- 키 입력 중 수정이 가능함
- BackSpace 입력 시, 이전에 입력된 키를 버퍼에서 삭제
프로그램은 사용자의 입력이 끝난 이후에 값을 읽음
Enter 키 : 키 입력의 끝을 의미함
- 해당 키가 눌린 시점부터, 키 입력 버퍼에서 프로그램이 값을 읽기 시작함
출력 스트림 버퍼
- 목적
- 프로그램에서 출력된 데이터를 출력 장치로 전송 전, 일시 저장
- 출력 장치를 반복적으로 사용하는 비효율성 개선
- 버퍼가 다 차거나 강제 명령 출력 시 출력 장치에 출력
- 목적
- 목적 :
표준 입출력 스트림
cin : istream 타입으로, 키보드와 연결
cout: ostream 타입으로, 스크린과 연결
cerr: ostream타입으로, 스크린과 연결(스트림 버퍼 - X, Error 출력)
clog: ostream타입으로, 스크린과 연결(스트림 버퍼 - O, Error 출력)
구분 클래스 내용 기본 스트림 ios 입출력 클래스들의 기본 클래스
스트림 클래스 공통 함수 및 상수 변수 선언문자 스트림 istream
ostream
iostreamisteam - 입력 스트림
ostream - 출력 스트림
iostream - 입출력 스트림파일 스트림 ifstream
ofstream
fstreamifstream - 파일에서 데이터를 읽을 때 사용
ofstream - 파일에 데이터를 쓸 때 사용
fstream - 파일에서 데이터를 읽고 쓸 때 사용ostream
사용방법
1
ostream& put(char ch) //ch 문자를 스트림 출력
1
ostream& write(char* str, int n) //str 배열의 n개 문자를 스트림 출력
1
ostream& flush()
예시
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
int main(){ //Hello! 출력하고 다음 줄로 이동 cout.put('H'); cout.put('e'); cout.put('l'); cout.put('l'); cout.put('o'); cout.put(33); cout.put('\n'); //C++ 출력 cout.put('C').put('+').put('+').put(' '); char str[] = "Hello World"; cout.write(str, 5); }
Output
1 2
Hello! C++ Hello
istream
int get()
- 입력 스트림에서 문자를 리턴
오류나 EOF(파일의 끝)는 -1 리턴
- 예시)
1 2 3 4 5
int ch; while ((ch == cin.get()) != EOF) { //EOF : -1 cout.put(ch); if (ch == '\n') break; //Enter키 입력시 읽기 중단
istream& get(char& ch)
- 입력 스트림에서 문자를 ch에 전달
- 오류는 내부 오류 플래그 리턴
- 예시
1 2 3 4 5 6
int ch; while (true) { //EOF : -1 cin.get(ch); //문자 읽기 if (cin.eof()) break; //EOF를 만날 경우 읽기를 중단 cout.put(ch); //ch의 문자 출력 }
예시
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
void get1() { cout << "Enter키가 입력될때까지 계속 입력 및 출력됨>>"; int ch; //EOF 비교를 위해 int while ((ch = cin.get()) != EOF) { //문자 읽기, EOF=-1 cout.put(ch); //읽은 문자 출력 if (ch == '\n') break; //Enter키 입력시 함수 종료 } } void get2() { cout << "Enter키가 입력될때까지 계속 입력 및 출력됨>>"; int ch; //EOF 비교를 위해 int while ((ch = cin.get()) != EOF) { //문자 읽기, EOF=-1 cout.put(ch); //읽은 문자 출력 if (ch == '\n') break; //Enter키 입력시 함수 종료 } }
Output
1 2 3 4
Enter키가 입력될때까지 계속 입력 및 출력됨>>Test1 Test1 Enter키가 입력될때까지 계속 입력 및 출력됨>>Test2 Test2
get1() -> get2() 순서로 진행되며, 값을 입력 후 Enter를 입력할 경우 다음 차례로 넘어감
문자열 입력
istream& get(char* s, int n)
- 입력 스트림으로부터 n-1개의 숫자를 읽고, s에 저장
- 마지막 글자 or \n을 만날 경우 \0을 삽입 및 종료됨
istream& getline(char* s, int n, char limit=’\n’)
- 위와 비슷하지만, limit에 지정된 문자를 스트림에서 제거함
입력 스트림 추가함수
istream& ignore(int n=1, int limit=EOF)
- 입력 스트림에서 n개의 문자 제거 및, limit 문자를 만날 경우 제거 및 리턴
int gcount()
- 최근 입력 스트림에서 읽은 바이트의 수를 리턴함
- Enter키도 개수에 포함됨
입력 스트림에서 문자 건너뛰기
예시
1 2 3 4 5
//입력 스트림에 입력된 문자 내에서 10개 제거 cin.ignore(10); //입력 스트림에서 10개 문자 제적 및, 제거 중 ';' 만날 경우 종료 cin.ignore(10, ';');
최근 읽은 ㅁ누자 개수
1 2 3 4 5
char line[80]; cin.getline(line, 80); //getline()) 함수에서 읽은 문자의 개수를 리턴 int n = cin.gcount();
포맷 입출력
1. 포맷 플래그
입출력 스트림에서 입출력 형식을 지정하기 위한 ios 클래스의 플래그
플래그 값 의미 ios::skipws 0x0001 입력 시, 공백문자를 무시 ios::unitbuf 0x0002 출력 스트림에 들어오는 데이터를 버퍼링하지 않고, 바로 출력 ios:uppercase 0x0004 16진수의 A~F, 지수 표현의 E를 대문자로 출력 ios::showcase 0x0008 16진수이면 0x, 8진수이면 0을 숫자 앞에 붙여 출력 ios::showpoint 0x0010 실수 값에 대해, 정수 부분과 더불어 소수점 이하의 끝자리들을 0으로 출력 ios:showpos 0x0020 양수에 대해 + 기호 출력 ios::left 0x0040 필드를 왼쪽 맞춤 형식으로 출력 ios::right 0x0080 필드를 오른쪽 맞춤 형식으로 출력 ios::internal 0x0100 부호를 왼쪾 맞춤으로, 숫자는 오른쪽 맞춤으로 출력 ios::dec 0x0200 10진수로 출력 및 디폴트로 설정 ios::oct 0x0400 8진수로 출력 ios::hex 0x0800 16진수로 출력 ios::scientific 0x1000 실수에 대해 과학 산술용 규칙에 따라 출력 ios:fixed 0x2000 실수에 대해 소수점 형태로 출력 ios::boolalpha 0x4000 설정될 경우, true를 “true”, false를 “false”로 출력
출력이 되지 않을 경우 , 정수 1과 0으로 출력함플래그를 세팅하는 멤버 함수
- long setf(long flags)
- flags를 스트림의 포맷 플래그로 설정하고 이전 플래그를 반환
- long unsetf(long flags)
- flags에 설정된 비트값을 스트림 포맷 플레그에서 해제 및 이전 플래그를 반환
예시
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
int main() { cout << 30 << endl; //10진수 출력 cout.unsetf(ios::dec); //10진수 해제 cout.setf(ios::hex); //16진수로 설정 cout << 30 << endl; cout.setf(ios::showbase); //16진수로 설정 cout << 30 << endl; cout.setf(ios::uppercase); //16진수의 A~F는 대문자로 출력 cout << 30 << endl; cout.setf(ios::dec | ios::showpoint); //10진수 표현과 동시에 소수점 이하 나머지는 0으로 출력 cout << 23.5 << endl; cout.setf(ios::scientific); //실수를 과학산술용 표현으로 출력 cout << 23.5 << endl; cout.setf(ios::showpos); //양수인 경우 + 부호도 함께 출력 cout << 23.5; }
Output
1 2 3 4 5 6 7
30 1e 0x1e 0X1E 23.5000 2.350000E+01 +2.350000E+01
- long setf(long flags)
2. 포맷 함수
정의
- 포맷을 변경하는 함수
종류
int width(int minWidth)
- 출력되는 필드의 최소 너비를 minWidth로 설정 및 이전 설정을 반환
char fill(char cFill)
- 필드의 빈칸을 cFill 문자로 채우고, 이전 설정을 반환
int precision(int np)
- 출력되는 수의 유효 숫자 자리 수를 np개로 설정(소수점은 제외)
예시
1
1
3. 조작자
- manipulator, 스트림 조작
- 조작자 : 함수
- C++ 표준 라이브러리에 구현된 조작자로 입출력 포맷의 지정이 목적임
- 다양한 목적으로 자신만의 조작자를 작성이 가능함
- 매개 변수가 없는 조작자 / 매개 변수를 보유한 조작자로 분류 가능
- 조작자는 항상 «나» 연산자와 함께 사용됨
- 매개변수를 가진 조작자는 **#include
** 필요
매개변수가 없는 조작자
1 2
cout << hex << showbase << 30 << endl; cout << dec << showpos << 100 << endl;
Output
1 2
0x1e +100
매개변수가 있는 조작자
1
cout << setw(10) << setfill('^') << "Test" << endl;Output
1
^^^^^^Test
예제
1 2 3 4 5 6 7 8 9 10 11 12 13 14
int main() { cout << showbase; //타이틀 출력 cout << setw(8) << "Number"; cout << setw(10) << "Octal"; cout << setw(10) << "Hexa" << endl; //하나의 수를 10, 8, 16진수 형태로 한줄에 출력 for (int i = 0; i < 50; i += 5) { cout << setw(8) << setfill('.') << dec << i; //10진수 cout << setw(10) << setfill('.') << oct << i; //8진수 cout << setw(10) << setfill('.') << hex << i << endl; //16진수
Output
1 2 3 4 5 6 7 8 9 10 11
Number Octal Hexa .......0.........0.........0 .......5........05.......0x5 ......10.......012.......0xa ......15.......017.......0xf ......20.......024......0x14 ......25.......031......0x19 ......30.......036......0x1e ......35.......043......0x23 ......40.......050......0x28 ......45.......055......0x2d
삽입 연산자와 추출 연산자
삽입 연산자
- « 연산자는 C++의 기본 연산자로 정수 시프트의 연산자
- ostream 클래스에 중복으로 작성되어 있음
추출 연산자
- ’»’ 연산자는 C++의 기본 연산자로, 삽입 연산자와 같이 정수 시프트의 연산장임
- ostream 클래스에 중복으로 작성되어 있음
14-1부터
파일 쓰기
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
int main()
{
//파일 출력 예제
char name[10], dept[20];
int sid;
//키보드로부터 읽기
cout << " 이름 : ";
cin >> name; //키보드에서 이름 입력 받음
cout << " 학번 : ";
cin >> sid;
cout << " 학과 : ";
cin >> dept;
//파일 열기 및 출력 스트림 생성
ofstream fd("D:\\23-2\\CPP\\test.txt");
if (!fd) { //열기 실패 검사
cout << "파일을 열수 없습니다.";
return 0;
}
//파일 쓰기
fd << name << endl; //name 쓰기
fd << sid << endl << endl;
fd << dept << endl;
cout << "파일 쓰기 성공" << endl;
fd.close(); //파일 닫기
}
Output
1
2
3
4
이름 : ABC
학번 : 20211111
학과 : Computer Engineering
파일 쓰기 성공
파일 모드
파일 모드 설정
파일 연결
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
int main()
{
//파일의 연결
const char* firstFile = "D:\\23-2\\CPP\\test_write2.txt";
const char* secondFile = "C:\\Windows\\system.ini";
fstream fout(firstFile, ios::out | ios::app); //쓰기 모드로 파일 열기
if (!fout) {
cout << firstFile << "열기 오류";
return 0;
}
fstream fin(secondFile, ios::in); //읽기 모드로 파일 열기
if (!fin) {
cout << secondFile << "열기 오류";
return 0;
}
int c;
while ((c = fin.get()) != EOF) //파일 끝까지 문자 읽기
fout.put(c); // 읽은 문자 기록
fin.close(); //입력 파일 닫기
fout.close(); //출력 파일 닫기
}
Output
1
2
3
4
5
6
7
8
9
10
11
12
13
14
; for 16-bit app support
[386Enh]
woafont=dosapp.fon
EGA80WOA.FON=EGA80WOA.FON
EGA40WOA.FON=EGA40WOA.FON
CGA80WOA.FON=CGA80WOA.FON
CGA40WOA.FON=CGA40WOA.FON
[drivers]
wave=mmdrv.dll
timer=timer.drv
[mci]
예외처리
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
int main()
{
//예외 처리
int n, sum, average;
while (true)
{
cout << "합을 입력하세요 : ";
cin >> sum;
cout << "인원수를 입력하세요 : ";
cin >> n;
try {
if (n <= 0) //오류 탐지
throw n; //catch(int x) 블록으로 점프
else
average = sum / n;
}
catch (int x) {
cout << "예외 발생 " << x << "으로 나눌 수 없음" << endl;
average = 0;
cout << endl;
continue;
}
cout << "평균 : " << average << endl << endl; //평균 출력
}
}
Output
1
2
3
4
5
6
7
합을 입력하세요 : 4
인원수를 입력하세요 : -4
예외 발생 -4으로 나눌 수 없음
합을 입력하세요 : 20
인원수를 입력하세요 : 4
평균 : 5
