Post

[Effective C++] Chapter 0

[Effective C++] Chapter 0

πŸ’™ref.

슀콧 λ§ˆμ΄μ–΄μŠ€, Effective C++ [3판], 곽용재(μ—­), ν”„λ‘œν…λ―Έλ””μ–΄, 2015


1. C++κΈ°λ³Έ μš©μ–΄

1.1. μ„ μ–Έ

μ„ μ–Έ (declaration)

  • μ½”λ“œμ— μ‚¬μš©λ˜λŠ” β€˜μ–΄λ–€ λŒ€μƒβ€™μ˜ 이름과 νƒ€μž…μ„ μ»΄νŒŒμΌλŸ¬μ—κ²Œ μ•Œλ¦Ό
    • ꡬ체적인 세뢀사항은 κΈ°μž¬ν•˜μ§€ μ•ŠμŒ


[code] declaration example
1
2
3
4
5
6
7
extern int x;	// 객체 μ„ μ–Έ
std::size_t numdigits(int number);	// ν•¨μˆ˜ μ„ μ–Έ

class Widget;	// 클래슀 μ„ μ–Έ

template<typename T>	// ν…œν”Œλ¦Ώ μ„ μ–Έ
class GraphNode;
  • int x : built-in(기본제곡) νƒ€μž…λ„ β€˜κ°μ²΄β€™μ— 포함

  • std namespace : C++의 ν‘œμ€€ 라이브러리 κ΅¬μ„±μš”μ†Œκ°€ λͺ¨λ‘ ν¬ν•¨λœ λ„€μž„μŠ€νŽ˜μ΄μŠ€

    • C의 λΌμ΄λΈŒλŸ¬λ¦¬μ™€ C++ λΌμ΄λΈŒλŸ¬λ¦¬μ— κ³΅ν†΅λœ κΈ°λŠ₯ 일뢀 λ‚΄μž₯
      • μ–΄λ–€ 헀더λ₯Ό #includeν•˜λŠλƒμ•  따라 라이브러리 κ²°μ •
  • size_t : λΆ€ν˜Έ μ—†λŠ” μ •μˆ˜ νƒ€μž…μ„ typedef둜 μ •μ˜

    • C++μ—μ„œ 개수λ₯Ό μ…€ λ•Œ size_t μ‚¬μš©

      eg) STL μ»¨ν…Œμ΄λ„ˆμ˜ μ›μ†Œ 개수 λ“±

    • 일반적으둜 operator[] ν•¨μˆ˜λ₯Ό κ°œλ°œμžκ°€ μ •μ˜ν•  λ•Œλ„ size_tλ₯Ό 받도둝 κ΅¬ν˜„ν•¨


1.2. μ‹œκ·Έλ„ˆμ²˜

μ‹œκ·Έλ„ˆμ²˜(Signature)

  • λͺ¨λ“  ν•¨μˆ˜μ˜ 선문에 λ‚˜μ˜€λŠ” λ§€κ°œλ³€μˆ˜ λ¦¬μŠ€νŠΈμ™€ λ°˜ν™˜ νƒ€μž…

    • numDigits ν•¨μˆ˜μ˜ μ‹œκ·Έλ„ˆμ²˜ : std::size_t(int)

      eg) int ν•˜λ‚˜λ₯Ό μ·¨ν•˜κ³  std::size_tλ₯Ό λ°˜ν™˜ν•˜λŠ” ν•¨μˆ˜

    단, β€˜μ‹œκ·Έλ„ˆμ²˜β€™μ˜ 곡식 C++ μ •μ˜μ—μ„œλŠ” ν•¨μˆ˜ λ°˜ν™˜ νƒ€μž…μ„ μ œμ™Έν•œλ‹€! νŽΈμ˜μ„±μ„ μœ„ν•΄ ν¬ν•¨ν–ˆλ‹€κ³  λ§ν•œλ‹€.


1.3. μ •μ˜

μ •μ˜(Definition)

  • μ„ μ–Έμ—μ„œ 빠진 ꡬ체적인 세뢀사항을 μ»΄νŒŒμΌλŸ¬μ—κ²Œ 전달
    • μ»΄νŒŒμΌλŸ¬λŠ” ν•΄λ‹Ή 객체에 λŒ€ν•œ λ©”λͺ¨λ¦¬ 마련
  • μ •μ˜ 제곡 κΈ°λŠ₯
    • ν•¨μˆ˜/ν…œν”Œλ¦Ώ μ •μ˜: μ½”λ“œ λ³Έλ¬Έ 제곡
    • 클래슀/ν…œν”Œλ¦Ώ μ •μ˜: 클래슀 ν˜Ήμ€ ν…œν”Œλ¦Ώ 멀버 제곡


[code] definition example
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 x;	// 객체 μ •μ˜

std::size_t numDigits(int number)	// ν•¨μˆ˜ μ •μ˜
{
    std::size_t digitSoFar = 1;
    
    while ((number/10) != 0) ++digitsSoFar;
    // λ°˜ν™˜ κ°’: λ§€κ°œλ³€μˆ˜μ— λ“€μ–΄ μžˆλŠ” 숫자 개수
    return digitsSoFar;
}

class Widget	// 클래슀 μ •μ˜
{
public:
    Widget();
    ~Widget();
    ...
};

template<typename T>	// 클래슀 ν…œν”Œλ¦Ώ μ •μ˜
class GraphNode
{
public:
    GraphNode();
    ~GraphNode();
    ...
};


1.4. μ΄ˆκΈ°ν™”

μ΄ˆκΈ°ν™”(Initialization)

  • μ–΄λ–€ 객체에 졜초의 값을 λΆ€μ—¬ν•˜λŠ” κ³Όμ •
    • μ‚¬μš©μž μ •μ˜ νƒ€μž…μœΌλ‘œ μƒμ„±ν•œ 객체의 경우, μƒμ„±μžμ— μ˜ν•΄ μ΄ˆκΈ°ν™”
  • κΈ°λ³Έ μƒμ„±μž(Default Constructor)
    • μ–΄λ–€ μΈμžλ„ 주어지지 μ•Šμ€ μƒνƒœλ‘œ 호좜될 수 μžˆλŠ” μƒμ„±μž
      • λ§€κ°œλ³€μˆ˜κ°€ μ—†κ±°λ‚˜ λͺ¨λ“  λ§€κ°œλ³€μˆ˜κ°€ κΈ°λ³Έ 값을 κ°–κ³  μžˆμ„ 경우


[code] Initialization example
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
// κΈ°λ³Έ μƒμ„±μž
class A
{
public:
	A();
};

// κΈ°λ³Έ μƒμ„±μž
class B
{
public:
	explicit B(int x = 0, bool b = true);
}

// κΈ°λ³Έ μƒμ„±μžx
class C
{
public:
	explicit C(int x);
}
  • explicit : μ„ μ–Έλœ μƒμ„±μžλŠ” μ•”μ‹œμ μΈ νƒ€μž… λ³€ν™˜μ„ μˆ˜ν–‰ν•˜λŠ” 데 쓰이지 μ•ŠμŒ
    • κ°œλ°œμžκ°€ μ˜ˆμƒν•˜μ§€ λͺ»ν•œ νƒ€μž… λ³€ν™˜ 방지
    • μ•”μ‹œμ  νƒ€μž… λ³€ν™˜μ— μƒμ„±μžκ°€ μ‚¬μš©λ˜μ§€ μ•ŠλŠ”λ‹€λ©΄ explicit선언을 적극 ꢌμž₯함!!


[code] explicit example
1
2
3
4
5
6
1. void doSomething(B bObject);
2. B bObj1;
3. doSomething(bObj1);
4. B bObj2;
5. doSomething(28);
6. doSomething(B(28))
  1. B νƒ€μž…μ˜ 객체λ₯Ό ν•˜λ‚˜ λ°›λŠ” ν•¨μˆ˜
  2. B νƒ€μž…μ˜ 객체
  3. B 객체λ₯Ό doSomething으둜 λ„˜κΉ€
  4. int인자 28λ‘œλΆ€ν„° B 객체 생성
  5. μ—λŸ¬! doSomething은 Bλ₯Ό μ·¨ν•΄μ•Ό 함(λ‹¨μˆœ int x)
  6. B 클래슀의 μƒμ„±μžλ‘œ intμ—μ„œ B둜 λͺ…μ‹œμ  λ³€ν™˜(μΊμŠ€νŒ…)


1.5. 볡사 μƒμ„±μž

볡사 μƒμ„±μž(Copy Constructor)

  • 객체 μ΄ˆκΈ°ν™”λ₯Ό μœ„ν•΄ 같은 νƒ€μž…μ˜ λ‹€λ₯Έ κ°μ²΄λ‘œλΆ€ν„° μ΄ˆκΈ°ν™”ν•  λ•Œ ν˜ΈμΆœλ˜λŠ” ν•¨μˆ˜
    • 값에 μ˜ν•œ 객체 전달을 μ •μ˜ν•˜λŠ” ν•¨μˆ˜!


볡사 λŒ€μž… μ—°μ‚°μž(Copy Assignment Operator)

  • 같은 νƒ€μž…μ˜ λ‹€λ₯Έ 객체에 μ–΄λ–€ 객체의 값을 λ³΅μ‚¬ν•˜λŠ” μš©λ„λ‘œ μ“°μ΄λŠ” ν•¨μˆ˜


[code] copy constructor 1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
class Widget
{
public:
	Widget();	// κΈ°λ³Έ μƒμ„±μž
	Widget(const Widget& rhs);	// 볡사 μƒμ„±μž
	Widget& operator=(const Widget& rhs);	// 볡사 λŒ€μž… μ—°μ‚°μž
	...
};

Widget w1;	// κΈ°λ³Έ μƒμ„±μž 호좜
Widget w2(w1);	// 볡사 μƒμ„±μž 호좜
w1 = w2;	// 볡사 λŒ€μž… μ—°μ‚°μž 호좜

Widget w3 = w2; // 볡사 μƒμ„±μž (!= 볡사 λŒ€μž… μ—°μ‚°μž)
  • w1 = w2 != Widget w3 = w2 // 볡사 μƒμ„±μž '='
    • μƒˆλ‘œμš΄ 객체가 μ •μ˜λ˜μ§€ μ•Šμ€ μƒν™©μ—μ„œ μƒμ„±μž 호좜 λΆˆκ°€λŠ₯
      • 볡사 λŒ€μž… 호좜
    • 객체가 μƒˆλ‘œ μ •μ˜λ  λ•ŒλŠ” μƒμ„±μžκ°€ 호좜
      • 볡사 λŒ€μž… 호좜 λΆˆκ°€λŠ₯


[code] copy constructor 2
1
2
3
4
bool hasAcceptableQuality(Widget w);
...
Widget aWidget;
if(hasAcceptableQuality(aWidget)) ...
  • w : hasAcceptableQuality ν•¨μˆ˜λ‘œ λ§€κ°œλ³€μˆ˜ 값이 λ„˜κ²¨μ§
    • μ‹€μ œ ν˜ΈμΆœμ—μ„œ aWidget => w둜 볡사

      • 볡사 κ³Όμ •μ—μ„œ Widget의 볡사 μƒμ„±μž μ‚¬μš©

      => *'값에 μ˜ν•œ 전달(pass-by-value)'* : 볡사 μƒμ„±μž 호좜


1.6. STL

  • ν‘œμ€€ ν…œν”Œλ¦Ώ 라이브러리

    • μ»¨ν…Œμ΄λ„ˆ, 반볡자, μ•Œκ³ λ¦¬μ¦˜ 및 이듀과 κ΄€λ ¨λœ κΈ°λŠ₯듀이 μ§‘κ²°ν•œ 결정체
    • ν•΄λ‹Ή κΈ°λŠ₯듀이 ν•¨μˆ˜ 객체둜 κ΅¬ν˜„λ˜μ–΄ 있음
      • ν•¨μˆ˜ κ°μ²΄λŠ” ν•¨μˆ˜ 호좜 μ—°μ‚°μž operator()λ₯Ό μ˜€λ²„λ‘œλ“œν•œ 클래슀둜 생성
  • λ―Έμ •μ˜ λ™μž‘(undefined behavior)

    • C++으둜 μ‚¬μš©λ˜λŠ” ꡬ문 μš”μ†Œλ“€ 쀑 λͺ‡ κ°œλŠ” λ™μž‘ μžμ²΄κ°€ μ •μ˜λ˜μ–΄ μžˆμ§€ μ•ŠμŒ

      => μ‹€ν–‰ μ‹œκ°„μ— μ–΄λ–€ ν˜„μƒμ΄ ν„°μ§ˆμ§€ ν™•μ‹€νžˆ 예츑 λΆˆκ°€λŠ₯

λ―Έμ •μ˜ λ™μž‘μ„ μΌμœΌν‚€λŠ” 예제

1
2
3
4
5
6
7
8
9
10
11
12
int *p = 0;			// p== 널포인터

// 널포인터λ₯Ό μ—­μ°Έμ‘°ν•˜λ©΄ λ―Έμ •μ˜ λ™μž‘ λ°œμƒ
std::cout << *p;

// name은 크기가 6인 λ°°μ—΄μž„
// λ¬Έμžμ—΄ 배열은 λ°˜λ“œμ‹œ λ§ˆμ§€λ§‰ λ„λ¬Έμž κ³ λ €ν•  것!!
char name[] = "Darla";

// μœ νš¨ν•˜μ§€ μ•Šμ€ λ°°μ—΄ μ›μ†Œμ§€μ •λ²ˆν˜Έλ‘œ μ°Έμ‘°ν•˜λ €κ³  ν•˜λ©΄ λ―Έμ •μ˜ λ™μž‘ λ°œμƒ
char c = name[10];


+) C++μ—μ„œλŠ” μΈν„°νŽ˜μ΄μŠ€ κΈ°λŠ₯을 μ œκ³΅ν•˜κ³  μžˆμ§€ μ•Šμ§€λ§Œ 순수 가상 ν•¨μˆ˜λ₯Ό 톡해 μΈν„°νŽ˜μ΄μŠ€ κΈ°λŠ₯을 κ΅¬ν˜„ν•  수 μžˆλ‹€.

  • ν΄λΌμ΄μ–ΈνŠΈ(client)
    • μΈν„°νŽ˜μ΄μŠ€λ₯Ό μ‚¬μš©ν•˜λŠ” λŒ€μƒ
      • ν•¨μˆ˜λ₯Ό ν˜ΈμΆœν•˜λŠ” μ½”λ“œ, μ½”λ“œλ₯Ό μž‘μ„±ν–ˆκ±°λ‚˜ μœ μ§€λ³΄μˆ˜ν•˜λŠ” μ‚¬λžŒ λ“±


2. ꡐ재 참고사항


2.1. 이름짓기에 λŒ€ν•œ κ·œμ•½

  • μ’Œλ³€κ³Ό μš°λ³€μ˜ μ•½μžλ₯Ό 각각 lhs, rhs둜 지정
    • 일반적으둜 이항 μ—°μ‚°μž(operator==, operator* λ“±)λ₯Ό κ΅¬ν˜„ν•˜λŠ” ν•¨μˆ˜μ˜ λ§€κ°œλ³€μˆ˜λ‘œ μ“°μž„
      • eg) operator*(a, b) => const Rational operator*(const Rational& lhs, const Rational rhs)l
  • 포인터 이름 μ„ μ–Έ μ‹œ, νƒ€μž… T의 객체에 λŒ€ν•œ 포인터λ₯Ό pt둜 μž‘μ„±
    • β€œT에 λŒ€ν•œ 포인터”


포인터 예제 μ½”λ“œ

1
2
3
4
5
6
7
Widget *pw;

class Airplane;
Airplane *pa;

class GameCharacter;
GameCharacter *pgc
  • μ°Έμ‘°μžμ— λŒ€ν•΄μ„œλ„ μœ μ‚¬ν•œ κ·œμΉ™ μ‚¬μš©
    • eg) Widget에 λŒ€ν•œ 참쑰자 rw


This post is licensed under CC BY 4.0 by the author.

Β© yejin. Some rights reserved.