E D R , A S I H C RSS

EffectiveC++

ž‘„ž: €˜ํ˜„(erunc0)

Effective C++ š”•ฝ

Contents

1. Shifting from C to C++
1.1. Item1: Prefer const and inline to #define
1.2. Item 2: Prefer iostream to stdio.h
1.3. Item 3: Prefer new and delete to malloc and free
1.4. Item 4: Prefer C++-style comments
2. Memory management
2.1. Item 5: Use the same form in corresponding uses of new and delete
2.2. Item 6: Use delete on pointer members in destructors
2.3. Item 7: Be prepared for out-of-memory conditions.
2.4. Item 8: Adhere to convention when writing operator new and operator delete
2.5. Item 9: Avoid hiding the "normal" form of new
2.6. Item 10: Write operator delete if you write operator new
3. Constructors, Destructors, and Assignment Operators (ํดž˜Šค— €ํ•œฒƒ“ค.)
3.1. Item 11: Declare a copy constructor and an assignment operator for classes with dynamically allocated memory
3.2. Item 12: Prefer initialization to assignment in constructors
3.3. Item 13: List members in an initialization list in the order in which they are declared
3.4. Item 14: Make sure base classes have virtual destructors
3.5. Item 15: Have operator= return a reference to *this
3.6. Item 16: Assign to all data members in operator=
3.7. Item 17: Check for assignment to self in operator=
4. Classes and Functions: Design and Declaration
4.1. Item 18. ตœ†Œํ•œ˜ ™„ „ํ•œ ํดž˜Šค ธํ„ฐํŽ˜ดŠค ถ”ตฌํ•œ‹ค.
4.2. Item 19. ฉค„ ํ•จˆ˜, „ฉค„ ํ•จˆ˜ ฐ ํ”„ Œ“œ ํ•จˆ˜ ตฌ„ํ•œ‹ค.
4.3. Item 20. ฐดํ„ฉค„ ณตšฉ(public) ธํ„ฐํŽ˜ดŠค— ํฌํ•จ‹œํ‚ค€ •ŠŠ”‹ค.
4.4. Item 21. €Šฅํ•œ const ดšฉํ•œ‹ค.
4.5. ํ•ญชฉ 22. ฐ’— ˜ํ•œ ํ˜ธถœณด‹คŠ”  ˆํŸฐŠค— ˜ํ•œ ํ˜ธถœ„ „ ํ˜ธํ•œ‹ค.
4.6. ํ•ญชฉ 23. ฐฒด ฐ˜ํ™˜‹œ  ˆํŸฐŠค ฐ˜ํ™˜ํ•˜€ •ŠŠ”‹ค.
4.7. ํ•ญชฉ 24. ํ•จˆ˜ ˜ค„กœ”ฉ ””ํดํŠธ ธžฐ’ ค‘—„œ ˜ŠฒŒ „ ํƒํ•œ‹ค.
4.8. ํ•ญชฉ 25. ํฌธํ„‚˜ ˆ˜˜ํ˜• ํƒ€ž…ƒ˜ ˜ค„กœ”ฉ„ ํ”ํ•œ‹ค.
4.9. ํ•ญชฉ 26. ž žฌ  ชจํ˜ธ„„ ฒฝ„ํ•œ‹ค.
4.10. ํ•ญชฉ 27. ˜„ํ•˜€ •Š€ ‚ด€ ƒ„ ฉค„ ํ•จˆ˜˜ ดšฉ„ ช…‹œ œกœ ง‰Š”‹ค.
4.11. ํ•ญชฉ 28.  „—ญ „ž„ŠคํŽ˜ดŠค „ํ• ํ•œ‹ค.
5. ํดž˜Šค™€ ํ•จˆ˜ : ตฌํ˜„
5.1. ํ•ญชฉ 29. ‚ด€ ฐดํ„— Œ€ํ•œ "ํ•ธ“ค"„ ฆฌํ„ดํ•˜Š” ฒƒ„ ํ”ํ•ด.
5.2. ํ•ญชฉ 30.  ‘ํ•˜ธฐ –ด คšด ฉค„— Œ€ํ•œ „ƒˆ˜ ํฌธํ„‚˜  ˆํŸฐŠค ฆฌํ„ดํ•˜Š” ฉค„ ํ•จˆ˜ ‚ฌšฉ„ ํ”ํ•˜.
5.3. ํ•ญชฉ 31. €—ญ ฐฒด— Œ€ํ•œ ฐธกฐ‚˜ ํ•จˆ˜ ‚ด—„œ new ดšฉํ•ด ดˆธฐํ™”œ ํฌธํ„ €ฆฌํ‚คŠ” ฐธกฐ ฆฌํ„ดํ•˜€ ง.
5.4. ํ•ญชฉ 32. €ˆ˜  •˜Š” €Šฅํ•œ ’คกœ Šฆถฐ.
5.5. ํ•ญชฉ 33. ธธ„ „ „ œกœ ‚ฌšฉํ•˜.
5.6. ํ•ญชฉ 34. ํŒŒ„˜ ปดํŒŒ ˜กด„(dependency)„ ตœ†Œํ™”ํ•˜.
6. ธŠคํ„Šค™€ ฐฒด€ํ–ฅ „„
6.1. ํ•ญชฉ 35. public „Šด "isa" ชจธงํ•˜„ก ํ•˜.
6.2. ํ•ญชฉ 36. ธํ„ฐํŽ˜ดŠค „Š ตฌํ˜„ „Š˜ ฐจด „ ดํ•ดํ•˜.
6.3. ํ•ญชฉ 37. „Šœ „€ƒ ํ•จˆ˜ žฌ •˜ํ•˜€ •Š„ก ํ•œ‹ค.
6.4. ํ•ญชฉ 38. „Šœ €žฌ ธžฐ’„ žฌ •˜ํ•˜€ •Š„ก ํ•œ‹ค.
6.5. ํ•ญชฉ 39. „ธต„˜ •„ž˜ชฝ ํดž˜Šค ‹คšดบŠคํŠธ(downcast)ํ•˜€ •Š„ก ํ•œ‹ค.
6.6. ํ•ญชฉ 40.  ˆด–ดง(layering)„ ํ†ตํ•ด "€€ณ  žˆŠ”" ฒƒ "‚ฌšฉํ•˜—ฌ ตฌํ˜„œ" ฒƒ„ ชจธงํ•˜„ก ํ•˜ž.
6.7. ํ•ญชฉ 41. „Š ํ…œํ”Œฆฟ˜ ฐจด „ ดํ•ดํ•œ‹ค.
6.8. ํ•ญชฉ 42. private „Š„ ฐ”ฅดฒŒ ‚ฌšฉํ•˜.
6.9. ํ•ญชฉ 43. ‹คค‘ „Š„ ฐ”ฅดฒŒ ‚ฌšฉํ•˜„ก ํ•˜.
6.10. ํ•ญชฉ 44. ˜ธํ•˜Š” ฐ” ํ‘œํ˜„ํ•˜„ก ํ•˜. ž‹ ด ํ‘œํ˜„ํ•œ ฒƒ˜ ˜ ดํ•ดํ•˜„ก ํ•˜.
7. ฌ˜ํ•œ €„
7.1. ํ•ญชฉ 45. C++€ €€ํ•˜ฒŒ –ด–ค ํ•จˆ˜ งŒ“ค–ดณ  ํ˜ธถœํ•˜Š”€ ดํ•ดํ•˜ธฐ
7.2. ํ•ญชฉ 46. ‹คํ–‰ ‹œ„ —Ÿฌณด‹คŠ” ปดํŒŒ ‹œ„ งํฌ ‹œ„ —Ÿฌ€ ข‹‹ค.
7.3. ํ•ญชฉ 47. „€—ญ  • (Non-local static) ฐฒดŠ” ‚ฌšฉ˜ธฐ  „— ดˆธฐํ™”˜„ก ํ•ด• ํ•œ‹ค.
7.4. ํ•ญชฉ 48. ปดํŒŒŸฌ˜ ฒฝณ (Warning)— ˜ ธฐšธ—ฌ.
7.5. ํ•ญชฉ 49. ํ‘œ€ ดธŒŸฌฆฌ ž˜ •Œ•„‘ž.
7.6. ํ•ญชฉ 50. C++— Œ€ํ•œ ดํ•ด „“ํ˜€.
8. Thread

1. Shifting from C to C++

1.1. Item1: Prefer const and inline to #define

preprocessor( „ฒ˜ฆฌธฐ)ณด‹คŠ” compiler „ ํ˜ธํ•œ‹คŠ” œป.

DeleteMe #define(preprocessor)ฌธ— Œ€ํ•ด const™€ inline„(compile)˜ ดšฉ„ ถ”ฒœํ•œ‹ค. --ƒ

-> const

~cpp 
   #define ASPECT_RATIO 1.653
ASPECT_RATIOŠ” †ŒŠคฝ”“œ€ ปดํŒŒกœ “ค–ด€ธฐ  „—  „ฒ˜ฆฌธฐ— ˜ํ•ด  œœ‹ค.

instead of upper..


define œ ASPECT_RATIO ž€ ƒˆ˜Š” 1.653œกœ €ฒฝ˜ธฐ•Œฌธ— ปดํŒŒŸฌŠ” ASPECT_RATIO ž€ฒƒด žˆ‹คŠ” ฒƒ„ ชจฅดณ  symbol table —?“ค–ด€€ •ŠŠ”‹ค. ดŠ” debugging„ ํ• •Œ ฌธ œ€ ฐœƒํ•  ˆ˜ žˆ‹ค. -ธํƒ
~cpp 
   const double ASPECT_RATIO = 1.653
…—„œ –ธธ‰ํ•œ ‘€€.

~cpp 
1. ƒˆ˜ ํฌธํ„ฐ(constant pointer)  •˜ํ•˜ธฐ€ ‹ค†Œ Œ‹คกœ›Œ „‹คŠ” ฒƒ.
   - ex -   
   const char * const authorName = "Scott Meyers";

2. ƒˆ˜˜ ˜—ญ„ ํดž˜Šคกœ  œํ•œํ•˜ธฐ œ„ํ•ด„  ƒˆ˜ ฉค„กœ งŒ“ค–ด• ํ•˜ฉฐ
   ทธ ƒˆ˜— Œ€ํ•œ ‹จ ํ•œฐœ˜ ณต‚ฌณธด žˆ‹คŠ” ฒƒ„ ํ™•‹ ํ•˜ธฐ œ„ํ•ด„œ staticœกœ
   ฉค„ €ˆ˜ งŒ“ค–ด• ํ•œ‹ค.
   - ex -
   // header.
   class GamePlayer 
   {
   private:
         static const int NUM_TURNS = 5;   // ƒˆ˜ „ –ธ! („ –ธงŒ ํ•œฒƒž„)
         int scores[NUM_TURNS];            // ƒˆ˜˜ ‚ฌšฉ.
   }

   // source file
   ...
   const int GamePlayer::NUM_TURNS;        //  •˜ ญํ•ด–ด• ํ•œ‹ค.
   ...


#define -> inline (งคํฌกœ ‚ฌšฉ‹œ)
  • inline: ํ•จˆ˜ ํ˜ธถœกœ ธํ•œ ˜ค„ํ—ค“œ „ˆ˜ žˆŠ”.. ‹œธฐ. ถธˆํ•˜ฉด …ฐพ•„ณด„š”.

~cpp 
   - ex -
   #define max(a,b) ((a) > (b) ? (a) : (b))
       // งคํฌกœ ž‘„‹œ—Š” –ธ œ‚˜ งคํฌกœ ชธฒด˜ ชจ“  ธž“ค„ „ํ˜ธกœ ฌถ–ด –ด• ํ•œ‹ค.
       // ™œธ€Š” ‹ค“ค •Œฒƒด‹ค. 
   
   // #define „ inlineœกœ..
   inline int max(int a, int b) { return a > b ? a : b; } // intํ˜•œกœงŒ  œํ•œ ˜–ดžˆ„ค.. 

   // templateœกœ
   template class<T>
   inline const T& max (const T& a, const T& b) { return a > b ? a : b; }
const™€ inline„ “ฐžŠ” –˜ธฐ˜€Šต‹ˆ‹ค. --; ™œ ทธŸฐ€Š” •„‹œŠ” „ป˜„œ €€ ‚จธฐ‹œตฌš”. ^^

#define ฌธ„ const™€ inlineœกœ Œ€ฒดํ•ด„œ จ„, #ifdef/#ifndef - #endif “.. ด™€ œ ‚ฌํ•œ ฒƒ“ค€

•„งŒ€ œ šฉํ•˜ฒŒ ‚ฌšฉ˜€กœ, •ˆ“ธํ•„š”Š” —†ฒ ฃ ?

งคํฌกœŠ” ง ทธŒ€กœ ˜ํ™˜ดธฐ •Œฌธ— „ทธ ฐœƒํ•  ํ™•ฅ ด †’Œ. ƒˆ˜„ –ธด‚˜ ํ•จˆ˜„ –ธฐ™€ ฒฝšฐŠ” €ธ‰  const ‚˜ inlineœกœ Œ€ฒดํ•˜Š”ฒŒ ข‹ฒ €. (œ.. ทธž˜„ ‹ค œกœ งค•ŒŠ” ƒˆ˜ „ –ธํ• •ŒŠ” #define ‚จšฉ ฒฝํ–ฅด..

ทธŸ.. ํ•ญชฉ1 end.

ํšก„ˆ˜„ค.

1.2. Item 2: Prefer iostream to stdio.h

scaf/printf -> cin/cout

1.3. Item 3: Prefer new and delete to malloc and free

* malloc & free
  • ƒ„ž(constructor)™€ †Œฉธž(destructor)˜ กดžฌ ชจฅธ‹ค.
* new & delete
  • ƒ„ž ฐ †Œฉธž™€   ˆํžˆ ƒํ˜ธ™ž‘ํ•˜ธฐ •Œฌธ—. they are clearly the superior choice.

1.4. Item 4: Prefer C++-style comments

/* */: C style˜ „

// : C++ style˜ „

žธฐงŒ˜ „„ “ฐฉด ˜Š”•„‹ˆ•? ‚œ. „‹คŠ”ฒŒ  œ ‹ซ€ฐ. ^^;

ช‡‹ฌ €‚œ ํ”„กœทธžจ€ žธฐ€ งŒ“ ฒŒ •„‹Œ•!? , ˜ˆ „— ƒด ํ˜•ด –˜ธฐํ•ด€.. --;; ใ…Žใ…Žใ…Ž ™ฐ..

2. Memory management

ฉ”ชจฆฌ ˜ฌฐ”กœ –ปŠ” ฒƒ ทธฒƒ„ ํšจœจ œกœ ˆ˜ํ–‰ํ•˜ฒŒ งŒ“œŠ”ฒƒ(?)— €ํ•œ –˜ธฐ“ค.

2.1. Item 5: Use the same form in corresponding uses of new and delete

~cpp 
string *stringArray = new string[100];
...
delete stringArray;   // delete ž˜ชป จ—ˆŠต‹ˆ‹ค.
// stringArray— ˜ํ•ด €ฅดœ„ 100ฐœ˜ string object“คค‘— 99ฐœŠ”  œŒ€กœ  œ€ •ˆจ.
  • new ํ˜ธถœํ• •Œ [] ดšฉํ–ˆ‹คฉด delete˜ ํ˜ธถœ‹œ—„ []ด šฉํ•œ‹ค. „‹จ„‹จ!
typedef ‚ฌšฉํ–ˆ„•Œ˜ delete.. --? : ƒˆกœšด ฌธ œ  œธฐ
~cpp 
typedef string AddressLines[4];      // ฐœธ †ŒŠ” 4ฐœ˜ „„ ฐจ€ํ•˜ณ 
                                     // ฐฐด ŠคํŠธงด‹ค.
...
string *pal = new AddressLines;      // "new AddressLines" returns a string *, just "new string[4]".. 
...
delete pal;     // –ด–ปฒŒ  € ชฐ~
delete [] pal;  // fine.
ดŸฐ ํ˜ž€(?)„ ํ”ํ•˜ธฐ œ„ํ•ด„  ฐฐ—ด ํƒ€ž…“ค— Œ€ํ•œ typedef ํ”ํ•˜ฉด ˜€ญ. ^^

2.2. Item 6: Use delete on pointer members in destructors

™  ฉ”ชจฆฌ ํ• ‹„ ํ–‰ํ•˜Š” ํดž˜Šค“ค€ ฉ”ชจฆฌ ํ• ‹ํ•˜ธฐ œ„ํ•ด„œ ƒ„ž— new “ด‹ค. (CString classฐ™€ฒƒ“ค?)

‚˜ค‘— ฉ”ชจฆฌ ํ•ด œํ•˜ธฐ œ„ํ•ด„œ †Œฉธž—„œ delete ‚ฌšฉํ•œ‹ค.

ทธŸฌ‚˜, ‚˜ค‘— ด ‡ฒŒ งŒ“  ํดž˜Šค ˆ„ตฐ€€ ฐœ„  ฒฝšฐ ทธฆฌณ , ฐœ„ œ ํดž˜Šค—„œ ํฌธํ„ฉค„ ถ”€ํ•˜ฒŒ

œ‹คฉด ฐ‘˜ „€€ ˆ™€ํ•˜ธธ ฐ”ž€‹ค.
  • Initialization of the pointer in each of the constructors. If no memory is to be allocated to the pointer in a particular constructor, the pointer should be initialized to 0 (i.e., the null pointer). - ƒ„ž ฐฐ—„œ ํฌธํ„ดˆธฐํ™”
  • Deletion of the existing memory and assignment of new memory in the assignment operator. - ํฌธํ„ฉค„— ‹ค‹œ ฉ”ชจฆฌ ํ• ‹ํ•  ฒฝšฐ ธฐกด˜ ฉ”ชจฆฌ ํ•ด œ™€ ƒˆกœšด ฉ”ชจฆฌ˜ ํ• ‹
  • Deletion of the pointer in the destructor. - †Œฉธž—„œ ํฌธํ„‚ญ œ
œ„˜ „€€ค‘ ฒ˜Œ˜ 2€€Š”  œŒ€กœ •ˆํ•ดฉด ฐ”กœฐ”กœ ˆˆ— „ดธฐ •Œฌธ— ดœฐฎ€งŒ,

„ฒˆงธ †Œฉธž—„œ ํฌธํ„‚ญ œ— €ํ•œ ฒƒ„  œŒ€กœ •ˆํ•ดฉด ฉ”ชจฆฌ œ ถœ(memory leak)œกœ ทธƒฅ ฒ˜ฆฌ˜ธฐ •Œฌธ— ํดž˜Šค— ํฌธํ„ฉค„ ถ”€ํ•  •Œงˆ‹ค ฐ˜“œ‹œ ช…‹ฌํ•ด• ํ•œ‹ค.

2.3. Item 7: Be prepared for out-of-memory conditions.

ฉ”ชจฆฌ€ €ํ• ฒฝšฐ   ˆํ•œ ฒ˜ฆฌ ํ•ด€‹คŠ” –˜ธฐธฒƒ ฐ™€ฐ...

ž˜ชจฅดฒ Œ. •„‹œŠ” „˜ „ช…ด งคšฐ ํ•„š”ํ•จ

Comment €ํƒํ•ดš”

ฉ”ชจฆฌ €‹œ— Œ€ํ•œ ˜ˆ™ธฒ˜ฆฌ Œ€„ํ•ด‘–ด  •„ฉด  ‹ํ•  ฒƒ ฐ™€ฐ.


set_new_handler ดšฉํ•œ memory ํ• ‹ ‹คํŒจฒ˜ฆฌ.

~cpp 
typedef void (* new_handler) {}; // ํ•จˆ˜ pointer
new_handler set_new_handler (new_handler p) throw ();
...
// —ฐ‚ฐž new€ ถฉ„ํ•œ ฉ”ชจฆฌ ํ• ‹ํ•˜€ ชปํ•  ฒฝšฐ ํ˜ธถœ  ํ•จˆ˜
void noMoreMemory ()
{
    cerr << "Unable to satisfy request for memory\n";
    abort ();
}
...
void main ()
{
    set_new_handler (noMoreMemory);
    int *pVigdataArray = new int [100000000]; // 100000000ฐœ˜  •ˆ˜ณต„„ ํ• ‹ํ•  ˆ˜ —†‹คฉด noMoreMemory€ ํ˜ธถœ.
    ...
}


ทธฆฌณ , class‚ด —„œ operator new™€ set_new_handler  •ํ•ด คŒœกœจ ํ•ด‹ classงŒ˜ …ํŠ(?)ํ•œ

™ž‘„ ตฌํ˜„ํ•  ˆ˜ žˆ‹ค.
~cpp 
class X {
public:
  static new_handler set_new_handler(new_handler p);
  static void * operator new(size_t size);
private:
  static new_handler currentHandler;
};
...
// source file (??.cpp)

new_handler X::currentHandler;      // sets currentHandler
                                    // to 0 (i.e., null) by
                                    // default
new_handler X::set_new_handler(new_handler p)
{
  new_handler oldHandler = currentHandler;
  currentHandler = p;
  return oldHandler;
}

void * X::operator new(size_t size)
{
  new_handler globalHandler =                // install X's
    std::set_new_handler(currentHandler);    // handler
  void *memory;
  try {                                      // attempt
    memory = ::operator new(size);           // allocation
  }
  catch (std::bad_alloc&) {                  // restore
    std::set_new_handler(globalHandler);     // handler;
    throw;                                   // propagate
  }                                          // exception

  std::set_new_handler(globalHandler);       // restore
                                             // handler
  return memory;
}
...
void noMoreMemory();                           // decl. of function to
                                               // call if memory allocation
                                               // for X objects fails
...
X::set_new_handler(noMoreMemory);
                                               // set noMoreMemory as X's
                                               // new-handling function

X *px1 = new X;                                // if memory allocation
                                               // fails, call noMoreMemory

string *ps = new string;                       // if memory allocation
                                               // fails, call the global
                                               // new-handling function
                                               // (if there is one)

X::set_new_handler(0);                         // set the X-specific
                                               // new-handling function
                                               // to nothing (i.e., null)

X *px2 = new X;                                // if memory allocation
                                               // fails, throw an exception
                                               // immediately. (There is
                                               // no new-handling function
                                               // for class X.)

‚ด ƒฐ—Š” ดŸฐฒŒ žˆ‹คณ งŒ •Œ•„‘ฉด ข‹„ฒƒ ฐ™‹ค. --;

2.4. Item 8: Adhere to convention when writing operator new and operator delete

operator new ™€ operator delete ˜ ž‘„‹œ ”ฐ• ํ• ฒƒ“ค.

''- ํ• ‹ ฃจํ‹ด“คด new ํ•ธ“คŸฌ ํ•จˆ˜(memory ํ• ‹‹œ ˜ˆ™ธ ฒ˜ฆฌฐ™€ “ค) €›ํ•˜ณ 

ํฌธฐ€ 0ธ š”ตฌ“ค„ ˜ฌฐ”กœ ฒ˜ฆฌํ•  ˆ˜ žˆ‹ค.

- ํ• ‹ํ•ด œ ฃจํ‹ด“คด „ ํฌธํ„— Œ€ฒ˜ํ•  ˆ˜ žˆ‹ค.
''



ฉค„€ •„‹Œ operator new
~cpp 
// operator new
void * operator new (size_t size)
{
if (size == 0) {                      // handle 0-byte requests
    size = 1;                           // by treating them as
  }                                     // 1-byte requests

  while (1) {

    // size bytes ํ• ‹..

    if (the allocation was successful)
      return (a pointer to the memory);
    
    new_handler globalHandler = set_new_handler(0);
    set_new_handler(globalHandler);

    if (globalHandler) (*globalHandler)();
    else throw std::bad_alloc();
  }

}
operator new € ํ•˜€ ํดž˜Šคกœ ƒ†œ‹คฉด –ด–ปฒŒ  Œ?

œ„˜ ฉ”ชจฆฌ ํ• ‹ €„„ ณดฉด size bytesงŒํ ฉ”ชจฆฌ ํ• ‹ ํ•˜ฒŒ œ‹ค.

ทธŸฐฐ, ด ํดž˜Šค œ„ํ•ด งŒ“ค–ด„ operator new —ฐ‚ฐž€ ƒ†  ฒฝšฐ.

ƒ†ฐ›€ ํดž˜Šค‚ด— operator new—ฐ‚ฐž ‹ค‹œ žฌ •˜ ํ•ดค˜• ํ•œ‹ค.

ทธŸ ฐ‘˜ source...
~cpp 
// in class
class Base {
public:
  static void * operator new(size_t size);
  ...
};

class Derived: public Base       // Derived doesn't declare
{ ... };                         // operator new

...
Derived *p = new Derived;        // calls Base::operator new!

// งŒ Base˜ operator new€ ด— Œ€ฒ˜ํ•˜ธฐ œ„ํ•ด „„˜€ •Š•˜‹คฉด ทธ 
// œ„ํ•œ ตœ„ ˜ ฐฉฒ•€ ‹คŒ ฐ™ด "ž˜ชปœ" –‘˜ ฉ”ชจฆฌ š”ฒญํ•˜ณ  žˆŠ”
// ํ˜ธถœ“ค„ ํ‘œ€ operator newกœ  „‹ฌํ•˜Š” ฒƒด‹ค
void *Base::operator new (size_t size)
{
  if (size != sizeof (Base))      // size€ ž˜ชป ˜—ˆœฉด
    return ::operator new (size); // š”ตฌ ฒ˜ฆฌํ•œ‹ค

  ... // ทธ ‡€ •Šœฉด —ฌธฐ„œ š”ตฌ ฒ˜ฆฌํ•จ
}
ฉค„€ •„‹Œ operator delete
~cpp 
// operator delete
void operator delete(void *rawMemory)
{
  if (rawMemory == 0) return;    // do nothing if the null
                                 // pointer is being deleted

  // deallocate the memory pointed to by rawMemory;

  return;
}
ด —ฐ‚ฐž„ —ญ‹œ ƒ†  ฒฝšฐ •ฝ„ ณจ˜•„ํ”ˆ€?

ดฒƒ —ญ‹œ ฉ”ชจฆฌ ํ•ด œํ•  ฒƒ˜ size „–ด„œ ํ•ด œํ•˜ธฐ •Œฌธ—.

operator new—ฐ‚ฐžฒ˜Ÿ ž˜(?) ฒ˜ฆฌ ํ•ด–ด• ํ•œ‹ค.
~cpp 
// in class
class Base {                       // same as before, but now
public:                            // op. delete is declared
  static void * operator new(size_t size);
  static void operator delete(void *rawMemory, size_t size);
  ...
};

void Base::operator delete(void *rawMemory, size_t size)
{
  if (rawMemory == 0) return;      // check for null pointer

  if (size != sizeof(Base)) {      // if size is "wrong,"
    ::operator delete(rawMemory);  // have standard operator
    return;                        // delete handle the request
  }

  // deallocate the memory pointed to by rawMemory;

  return;
}

2.5. Item 9: Avoid hiding the "normal" form of new

„‹จ. class ‚ด— operator new งŒ“ค–ด „•Œ.

~cpp 
class X {
public:
  void f();

  // new ํ•ธ“คง ํ•จˆ˜˜ ‚ฌ–‘„ งŒํ•˜Š” —ฐ‚ฐž new
  static void * operator new(size_t size, new_handler p);
};

void specialErrorHandler();     // definition is elsewhere

X *px1 =  new (specialErrorHandler) X; // calls X::operator new

X *px2 = new X;   // error!, " •ƒ form— Œ€ํ•ด ํ˜ธํ™˜ด ดฃจ–ด €€•ŠŠ” ฌธ œ ."

œ„˜ ฌธ œ ํ•ดฒฐํ•˜ธฐ œ„ํ•ด.
~cpp 
class X 
{
public:
  void f();
  static void * operator new(size_t size, new_handler p);
  static void * operator new(size_t size) // normal formํ˜•‹˜ —ฐ‚ฐž„ งŒ“ค–ด€‹ค.
  { return ::operator new(size); }
};
X *px1 =
  new (specialErrorHandler) X;      // calls X::operator
                                    // new(size_t, new_handler)
X* px2 = new X;                     // calls X::operator
                                    // new(size_t)
or
~cpp 
class X 
{
public:
  void f();
  static
    void * operator new(size_t size,                
                        new_handler p = 0);         // default ฐ’„ –ด„œ ฒ˜ฆฌํ•ด€‹ค
};
X *px1 = new (specialErrorHandler) X;               // ok
X* px2 = new X;                                     // ok
–ด–ค ฐฉฒ•ด“  ƒ€ —†€งŒ, code •ฝ„ด„ œ˜Š” defaut ธž Š”ฒƒด.. ใ…กใ…ก;; ํ•˜ํ•˜

2.6. Item 10: Write operator delete if you write operator new

operator new ™€ operator deleteŠ” ™œ “ธŒ?

ํšจœจ„ •Œฌธดž‹ˆ‹ค. ƒˆกœ ž‘„ํ•ดŠ”ฒŒ –งˆ‚˜ ํฐ ํšจœจ„ ณดดธฐ— defaultกœ  œณตํ•ดŠ” ฒƒ„

“ฐ€ •ŠŠ” ฒƒŒ? --a ‚ฌ‹ค ชฐžŠ”ฐ, ฐ˜  € new (default new—ฐ‚ฐž) ‚ฌšฉํ•˜ฒŒ ˜ฉด ํ• ‹œ ธ”ก˜

ํฌธฐ ‚˜ํƒ€‚ด Š” ถ”€ ธ  •ณด ฐ™ด ถ™—ฌ memory ํ• ‹ํ•ด €‹คณ  ํ•ฉ‹ˆ‹ค. ทธŸฐฐ, operator new—ฐ‚ฐž

ง ‘งŒ“ค–ด ฒŒ˜ฉด ดŸฐ ถ”€  •ณด •Šถ™—ฌค˜„ œ‹คŠ” ตฐš”. ทธŸฌ‹ˆŒ ถ”€  •ณด ํฌธฐงŒํ˜ †‹ค„ „ ˆ˜

žˆ‹คŠ” งด€š”~ ํ•œ‹คงˆ””กœ ํšจœจ„ด ข‹•„กŒ‹ค.(ฐ˜ฉด ::operator newŠ” œ —ฐ„ด ข‹‹ค)

...


DeleteMe ทธŸฐ ˜ณด‹ค String ด‚˜, linked list ํ˜€ ธฐํƒ€ —ฌŸฌ ธฐํƒ€ ฐดํ„ฐ ํ˜•œกœ งŽ€ ˆ˜˜ ํ• ‹„ ํ†ตํ•ด„œ “ธˆ˜ žˆŠ” ธž˜ ฒฝšฐ—Š” ‚ฌšฉž  •˜ new ดšฉํ•˜—ฌ €Šฅํ•˜ฉด ณตšฉ ฉ”ชจฆฌ ณต„—„œ ํ™œ™‹œœ„œ, ฉ”ชจฆฌ ํ• ‹ ฝ”“œ „ดณ  (ฉ”ชจฆฌ ํ• ‹˜ new™€ allocŠ” „Šฅ— งŽ€ ˜ํ–ฅ„ ‹ˆ‹ค.) ฉ”ชจฆฌ „ดณ  ํšจœจ  €ฆฌ ํ• ˆ˜ žˆ‹คŠ” ˜ฐ™Šต‹ˆ‹ค. ทธŸฐ ฐดํ„ฐ ํ˜•œกœ “ฐดŠ” ธž€ •„‹Œ ํ•œ app•ˆ—„œ ‹จ ํ•œฒˆงŒ ‚ฌšฉ˜Š” ํดž˜Šคฉด ตฌ€ new „˜ํ•ด„œ memory leak˜ œ„ํ—˜„„ ฆ€ ‹œํ‚คŠ” ฒƒณด‹ค, ฐ˜ ธ new™€ ƒ„ž ํŒŒดดž˜ ทœ™„ “ฐŠ”ฒƒด ข‹„ฒ‹ˆ‹ค. --ƒ

3. Constructors, Destructors, and Assignment Operators (ํดž˜Šค— €ํ•œฒƒ“ค.)

„ ํ•˜ธฐ ‰ฌšด ƒ„ž, †Œฉธž, ˜ํ™˜ —ฐ‚ฐž— Œ€ํ•œ –˜ธฐ“ค.

3.1. Item 11: Declare a copy constructor and an assignment operator for classes with dynamically allocated memory

~cpp 
// ™„ฒฝํ•˜€ •Š€ String class
class String {
public:
  String(const char *value);
  ~String();
private:
  char *data;
};

String::String(const char *value)
{
  if (value) {
    data = new char[strlen(value) + 1];
    strcpy(data, value);
  }
  else {
    data = new char[1];
    *data = '\0';
  }
}

inline String::~String() { delete [] data; }
ด class—Š” ˜ํ™˜ —ฐ‚ฐž‚˜ ณต‚ฌ ƒ„ž€ —†‹ค. ดŸฐ ํดž˜ŠคŠ” ข‹€ ชปํ•œ ฒฐ ฐœƒ‹œํ‚จ‹ค.



ฐฒด a˜ ํฌธํ„Š” ฌธž—ด "Hello", ฐฒด b‚ด˜ ํฌธํ„Š” "World"ฌธž—ด„ ‹ดณ  žˆŠ” ฉ”ชจฆฌ €ฆฌํ‚จ‹ค.

‹คŒ ฐ™€ ˜ํ™˜—ฐ‚ฐ„ ํ•˜ฉด..
~cpp 
b = a;
ํดž˜Šค ‚ด— operator=€  •˜ ˜–ด žˆ€ •Šธฐ •Œฌธ—, C++—„œ default ˜ํ™˜ —ฐ‚ฐž ํ˜ธถœํ•œ‹ค.

default ˜ํ™˜ —ฐ‚ฐžŠ” ํดž˜Šค˜ ฉค„ €ˆ˜“ค„ ํ•˜‚˜”ฉ ˜ํ™˜ํ•˜Š” ž‘—…„ ํ•˜ธฐ •Œฌธ— a™€ b˜ ฉค„ €ˆ˜ data

ง ‘ ณต‚ฌ ํ•œ‹ค.



ด ƒํƒœŠ”  –ด„ ‘€€˜ ฌธ œ „ €€ณ  žˆ‹ค.

  • b—„œ €ฆฌํ‚คณ  žˆ˜ ฉ”ชจฆฌ€ ‚ญ œ ˜€ •Š•˜€ •Œฌธ—, ˜›ํžˆ –ด„ฆฌฒŒ ˜Š” ฌธ œ ธ memory leak.
  • a™€ bชจ‘ ฐ™€ ฌธž—ด„ €ฆฌํ‚คŠ” ํฌธํ„ ฐ–ฒŒ ˜—ˆœ€กœ ‘˜ค‘ํ•˜‚˜€ €›Œ€ฒŒ ˜ฉด ‚˜จธ€ ํ•˜‚˜—ญ‹œ ฐดํ„ žƒ–ด „ฆฌฒŒ œ‹ค.
‘ฒˆงธ ƒํ™ฉ˜ ˜ˆ.
~cpp 
String a("Hello");      // a ƒ„
...
{                       // ƒˆกœšด ˜—ญ
  String b("World");    // b ƒ„
  ...

  b = a;          // default ˜ํ™˜ —ฐ‚ฐž ˆ˜ํ–‰
                     // b˜ ฉ”ชจฆฌ žƒฒŒ œ‹ค.

}                 // ˜—ญด ‹ซํžŒํ›„,
                  // b˜ †Œฉธž€ ํ˜ธถœœ‹ค. ทธŸฌ€กœ, a€ €ฆฌํ‚ค˜ data„ †Œฉธ˜ฒŒ œ‹ค.

String c = a;     // c˜ dataŠ”  •˜ ˜€ •ŠŠ”‹ค. 
                  // ณต‚ฌ ƒ„ž€  •˜ ˜€ •Š•˜ธฐ •Œฌธ— C++—„œ  œณตํ•˜Š” default ˜ํ™˜ —ฐ‚ฐž ํ˜ธถœ.
                  // a˜ dataŠ” ด€›Œ กŒธฐ •Œฌธ— memory leak˜ ฌธ œŠ” —†‹ค.
                  // ทธŸฌ‚˜, c™€ aŠ” ฐ™€ ณณ„ €ฆฌํ‚จ‹ค. ทธฆฌณ , c˜ †Œฉธž€ ํ˜ธถœ ˜ฉด œ„—„œ ‚ญ œœ ณณ„ ‹ค‹œํ•œฒˆ 
                     // ‚ญ œ ํ•˜ฒŒ œ‹ค. ฒฐ  œกœ a™€ c€ €ฆฌํ‚ค˜ ณณด ‘ฒˆ ‚ญ œ ˜Š” ฒฝšฐ€ ฐœƒœ‹ค. (a€ †Œฉธํ• •Œ, c€ †Œฉธํ• •Œ)
ดƒ ˜ํ™˜ —ฐ‚ฐž— €ํ•œฒƒ.
...

ดํ•˜ ณต‚ฌ ƒ„ž— €ํ•œฒƒ.
~cpp 
void doNothing(String localString) {}
...
String s = "The Truth Is Out There";
doNothing(s);  // deault ณต‚ฌ ƒ„ž ํ˜ธถœ. call-by-valueกœ ธํ•ด 
                 // localString€ s•ˆ— žˆŠ” ํฌธํ„— Œ€ํ•œ ณต‚ฌณธ„ €€ฒŒ œ‹ค.
// ทธž˜„œ, doNothingด ˆ˜ํ–‰„ งˆ˜ฉด, localString€ —ฌ—ญ„ ฒ—–ด‚˜ณ , †Œฉธž€ ํ˜ธถœœ‹ค.
// ทธ ฒฐ sŠ” localStringด ‚ญ œํ•œ ฉ”ชจฆฌ— Œ€ํ•œ ํฌธํ„ €€ฒŒ œ‹ค. (data †‹ค)
* ํดž˜Šค •ˆ— ํฌธํ„ กฐ” ฆฌŠ” ฉค„ €ˆ˜€ žˆ„ ฒฝšฐ—Š” ทธ ํดž˜Šค— ณต‚ฌ ƒ„ž™€, ˜ํ™˜ —ฐ‚ฐž  •˜ํ•ด –ด• ํ•œ‹ค...

3.2. Item 12: Prefer initialization to assignment in constructors

~cpp 
template<class T>
class NamedPtr {
public:
  NamedPtr(const string& initName, T *initPtr);
  ...

private:
  string name;
  T *ptr;
};
ฉค„ €ˆ˜ ดˆธฐํ™” ํ•˜Š” ฐฉฒ•.


1. ดˆธฐํ™” ฆฌŠคํŠธ ‚ฌšฉํ•œ‹ค.
~cpp 
template<class T>
NamedPtr<T>::NamedPtr(const string& initName, T *initPtr  )
: name(initName), ptr(initPtr) {}
2. ƒ„ž˜ ฝ”“œ €„—„œ ˜ํ™˜„ ํ•œ‹ค.
~cpp 
template<class T>
NamedPtr<T>::NamedPtr(const string& initName, T *initPtr)
{
  name = initName;
  ptr = initPtr;
}
2€€ ฐฉฒ•  •„กœ ฉค„ €ˆ˜ ดˆธฐํ™” ํ• ˆ˜ žˆŠ”ฐ. …—„œŠ” ดˆธฐํ™” ฆฌŠคํŠธ „ ํ˜ธํ•œ‹ค.

ฒซงธŠ” ดˆธฐํ™”งŒ €Šฅํ•œ constฉค„ €ˆ˜ ดˆธฐํ™” ํ• ˆ˜ žˆ‹คŠ” ˜—„œดณ ,

‘ฒˆงธŠ” ‹คšฉ˜(ํšจœจ„) ฐจ›—„œ ดˆธฐํ™” ฆฌŠคํŠธ „ ํ˜ธ ํ•œ‹คŠ” ฒƒด‹ค.

(™œ.. ํšจœจ„ด ข‹•„€Š”€Š” ฐž ƒฐ~ …—„ ‚˜™€žˆณ .. ƒฐงŒ ํ•ดณดฉด •Œˆ˜ žˆŠ” ฌธ œ~)


''
  • €Šฅํ•œ ฒฝšฐ ํ•ญƒ ฉค„ ดˆธฐํ™” ฆฌŠคํŠธ ‚ฌšฉํ•˜Š” Šต€„ “คดฉด, const™€  ˆํŸฐŠค €ˆ˜“ค— Œ€ํ•œ
    š”ตฌ กฐ„ „šธ ˆ˜ žˆ„ ฟงŒ •„‹ˆ, ฉค„ €ˆ˜“ค— Œ€ํ•œ „ํšจœจ ธ ดˆธฐํ™”„ „ˆ˜ žˆ‹ค.''

3.3. Item 13: List members in an initialization list in the order in which they are declared

ํดž˜Šค ฉค„“ค€ ํดž˜Šค— „ –ธœ ˆœ„œ— ”ฐ ดˆธฐํ™”œ‹ค.

ฉค„ ดˆธฐํ™” ฆฌŠคํŠธ— ‚˜—ดœ ˆœ„œŠ” •„ฌดŸฐ ˜ํ–ฅ„ ˜€ ชปํ•œ‹ค.

งŒ•ฝ, ดˆธฐํ™” ฆฌŠคํŠธ— ‚˜—ดœ ˆœ„œŒ€กœ ฉค„ €ˆ˜€ ดˆธฐํ™” œ‹คณ  € • ํ•˜ณ  ด ˜ˆ ณดž.

~cpp 
class Wacko {
public:
  Wacko(const char *s): s1(s), s2(0) {}
  Wacko(const Wacko& rhs): s2(rhs.s1), s1(0) {}

private:
  string s1, s2;
};

Wacko w1 = "Hello world!";
Wacko w2 = w1;
w1 w2˜ ฉค„“ค€ ‹คฅธ ˆœ„œ— ”ฐ ƒ„  ฒƒด‹ค. ทธฆฌณ , ‹ค‹œ ทธ ฐฒด“ค(string ฐฒด)„ †Œฉธํ•˜ธฐ œ„ํ•ด„œ

ฐฒด“ค(string ฐฒด)ด ƒ„œ ˆœ„œ ธฐ–ตํ•œ‹คŒ †Œฉธž ฐจ€Œ€กœ ํ˜ธถœํ•ด• ํ• ฒƒด‹ค. ดŸฐ overhead —†• ธฐ œ„ํ•ด,

ชจ“  ฐฒด— Œ€ํ•ด„œ ƒ„ž™€ †Œฉธž˜ ํ˜ธถœ ˆœ„œŠ” ™ํ•˜ฒŒ ˜–ด žˆณ , ดˆธฐํ™” ฆฌŠคํŠธ— ‚˜—ดœ ˆœ„œŠ” ฌด‹œœ‹ค.

‹จ, ดŸฐ ทœ™€ „ •  ฐดํ„ฉค„“คงŒ ”ฐฅธ‹ค.

 •  ฐดํ„“คด• ‹จ€ ํ•œฒˆงŒ ดˆธฐํ™” ˜ธฐ •Œฌธ— ดŸฐฒƒ„ ”ฐ ํ•„š”Š” —†‹ค.

3.4. Item 14: Make sure base classes have virtual destructors

ฒ ดŠค ํดž˜Šค˜ †Œฉธž €ƒํ•จˆ˜กœ ‘”‹คŠ” –˜ธฐŠ” ฒ ดŠค ํดž˜Šค€ „Š  ฒฝšฐ „Šœ ํดž˜Šค—‚ด—„œ †Œฉธž˜

ž‘šฉ„ ˜ฌฐ”กœ ํ•˜ธฐ œ„ํ•จด‹ค.  ‹ํ•œ ˜ˆ ณด„ก ํ•˜ž.

~cpp 
// base class
class EnemyTarget {
public:
  EnemyTarget() { ++numTargets; }
  EnemyTarget(const EnemyTarget&) { ++numTargets; }
  ~EnemyTarget() { --numTargets; }
  static unsigned int numberOfTargets()
  { return numTargets; }
  virtual bool destroy();                 // EnemyTarget ฐฒด ํŒŒดด—
                                          // „ณตํ•˜ฉด ฐธ„ Œ ค €‹ค

private:
  static unsigned int numTargets;               // ฐฒด šดํ„ฐ
};
// class‚ด˜  •  €ˆ˜Š” ํดž˜Šค˜ ฐ”ชฝ—  •˜˜–ด• ํ•œ‹ค.
// ธฐณธ œกœ 0œกœ ดˆธฐํ™”œ‹ค.
unsigned int EnemyTarget::numTargets;
...
..
// base class ƒ†ํ•œ ํดž˜Šค
class EnemyTank: public EnemyTarget {
public:
  EnemyTank() { ++numTanks; }
  EnemyTank(const EnemyTank& rhs)
  : EnemyTarget(rhs)
  { ++numTanks; }
  ~EnemyTank() { --numTanks; }
  static unsined int numberOfTanks()
  { return numTanks; }
  virtual bool destroy();
private:
  static unsigned int numTanks;         // object counter for tanks
};
unsigned int EnenyTank::numTanks;
EnemyTarget˜ ฐฒด šดํŠธ ํ•˜ธฐ œ„ํ•ด  •  ฉค„ €ˆ˜ numTargets ‘—ˆœฉฐ EnemyTarget„ ƒ†ํ•œ EnemyTank—„œ„

ฐฒด˜ šดํŠธ œ„ํ•ด  •  ฉค„ €ˆ˜ numTanks ‘—ˆ‹ค.

ทธฆฌณค, ‹คŒ ฐ™€ code  šฉ‹œœณดž.
~cpp 
EnemyTarget *targetPtr = new EnemyTank;
...
delete targetPtr;  // •„ฌด ฌธ œ€ —†–ด ณดธ‹ค.
The C++ language standard is unusually clear on this topic. ฒ ดŠค ํดž˜Šค— Œ€ํ•œ ํฌธํ„ ‚ฌšฉํ•ด„œ „Šœ ํดž˜Šค

‚ญ œํ•˜ คณ  ํ•˜ฉฐ, ฒ ดŠค ํดž˜ŠคŠ” €ƒ †Œฉธž €€ณ  žˆ€ •Š€ ฒฝšฐ. ทธ ฒฐŠ”  •˜˜–ด žˆ€ •Š‹ค. ดฒƒ€ ปดํŒŒŸฌกœ

ํ•˜—ฌธˆ, ›ํ•˜Š” Œ€กœ ฝ”“œ ƒƒํ—ˆณ  ‹คํ–‰ํ•˜„ก ํ•˜Š” ฒฐ ดˆž˜ํ•œ‹ค. (‹คํ–‰ ‹œ„— ž ฐœƒํ•˜Š” ฒƒ€ „Šœ ํดž˜Šค˜ †Œฉธž€

ํ˜ธถœ˜€ •ŠŠ”‹คŠ” ฒƒด‹ค. œ„˜ ˜ˆ—„œ, targetPtrด ‚ญ œ  •Œ EnemyTank˜ ˆ˜€  œŒ€กœ กฐ •˜€ •ŠŠ”‹คŠ” ฒƒ„ ˜ธ ํ•œ‹ค.)

ทธž˜„œ ดฌธ œ ํ”ํ•˜ธฐ œ„ํ•ด„œ, EnemyTarget˜ †Œฉธž virtualกœ „ –ธํ•ด• ํ•œ‹ค. †Œฉธž €ƒํ•จˆ˜กœ „ –ธํ•˜ฉด, —ฌŸฌ„ด ›ํ•˜Š”

ฐฉ‹œกœ †Œฉธž€ ถˆฆฌ„ก ํ• ˆ˜ žˆ‹ค.

3.5. Item 15: Have operator= return a reference to *this

šฐฆฌŠ” šฐ„  operator=  •˜ ํ•ด„•Œ
~cpp 
w = x= y = z = "Hello"; 
ด Ÿฐ‹˜ —ฐ† ธ ˜ํ™˜ —ฐ‚ฐ„ ํ•  ˆ˜ žˆ–ด• ํ•œ‹ค. ทธ ‡ธฐ •Œฌธ— operator=—ฐ‚ฐž˜ ฆฌํ„ดํ˜•„ voidกœ  •˜ ํ•˜ฉด •ˆœ‹ค.

ทธฆฌณ , operator=—ฐ‚ฐž˜ ฆฌํ„ดํ˜•„ constกœ  •˜ ํ•ด —ˆ„•Œ. ฐ‘˜ ˜ˆ œ™€ ฐ™€ ฉฒญํ•œ(?) —ฐ‚ฐ„ ํ•ด—ˆ„•Œ  šฉ ˜€ •ŠŠ”‹ค. ฐ‘˜ —ฐ‚ฐ€ ฉฒญํ•œ(?) —ฐ‚ฐด€งŒ C++˜ ธฐณธ ํƒ€ž…— Œ€ํ•ด  €Ÿฐ —ฐ‚ฐด €Šฅํ•˜ธฐ •Œฌธ—  €Ÿฐ —ฐ‚ฐ„ €›ํ•˜ฒŒ ” งŒ“ค–ด• ํ•œ‹ค.
~cpp 
class Widget {
public:
  ...                                            // note
  const Widget& operator=(const Widget& rhs);    // const
  ...                                            // return
};                                               // type
...
Widget w1, w2, w3;
...
(w1 = w2) = w3;         // assign w2 to w1, then w3 to
                        // the result! (Giving Widget's
                        // operator= a const return value
                        // prevents this from compiling.)

ทธž˜„œ, operator=˜ ฆฌํ„ดํ˜•„ constกœ ž‘„ํ•˜ฉด •ˆœ‹ค. (....--;...)

...

ธฐณธ ํ˜•‹„ ฐ–Š” ˜ํ™˜ —ฐ‚ฐž—„œ, ฆฌํ„ฐ’œกœ ‚ฌšฉํ•  ˆ˜ žˆŠ” ‘ €€ ฒฝšฐ€ žˆ‹ค. ˜ํ™˜˜ ™ชฝ €„ (this) ˜ํ™˜˜ ˜คฅธชฝ €„(ธž ฆฌŠคํŠธ— žˆŠ”ฒƒ)ด‹ค. –ด–คฒƒ„ ฆฌํ„ดํ•ด „ฒƒธ€? operator= € จœ ฐ‘˜ ‘€€ ฒฝšฐ ณดž.
~cpp 
String& String::operator=(const String& rhs)
{
  ...
  return *this;            // return reference
                           // to left-hand object
}
String& String::operator=(const String& rhs)
{
  ...
  return rhs;              // return reference to
                           // right-hand object
}
œ„˜ ‘€€ ฒฝšฐŠ” „‹คฅธ ฐจด€ —†–ดณดธ‹ค. ทธŸฌ‚˜, ค‘š”ํ•œ ฐจด ด žˆœ‹ˆ ง„ ‚ดŠ” ฒƒด ฒ €? --;

ฒซงธ, rhs ฆฌํ„ดํ•˜Š” ฒฝšฐŠ” compile ˜€ •Š„ ฒƒด‹ค. ™œƒํ•˜ฉด, rhsŠ” const String— Œ€ํ•œ  ˆํŸฐŠค ดณ , operator=Š” String— Œ€ํ•œ  ˆํŸฐŠค ฆฌํ„ดํ•˜ธฐ •Œฌธด‹ค. ญ ดŸฐ ฌธ œ• ฐ‘—„œ ฒ˜Ÿ ณ ˜ฉด ฌธ œ ˜€ •ŠŠ”‹ค.
~cpp 
String& String::operator=(String& rhs)   { ... }
ํ•˜€งŒ, ดฒˆ—Š” ํดž˜Šค˜ operator= ‚ฌšฉํ•˜Š” ฝ”“œ—„œ ฌธ œ€ ฐœƒํ•œ‹ค.
~cpp 
x = "Hello";
˜ํ™˜˜ ˜คฅธชฝ €„ด Stringํ˜•ด •„‹ˆ char *ํ˜•ดธฐ •Œฌธ— ปดํŒŒŸฌŠ” String˜ ƒ„ž ํ†ตํ•ด ž„‹œ Stringฐฒด งŒ“ค–ด„œ ํ˜ธถœ„ ํ•œ‹ค. ฆ‰, •„ž˜™€ ฐ™€ code ƒ„ํ•œ‹ค.
~cpp 
const String temp("Hello"); // ž„‹œ ฐฒด งŒ“ ‹ค.
...
x = temp; // ž„‹œ ฐฒด operator=—  „‹ฌํ•œ‹ค.
ปดํŒŒŸฌŠ” œ„™€ ฐ™€ ž„‹œ ฐฒด งŒ“ค คณ  ํ•˜€งŒ, ž„‹œ ฐฒด€ constŠ” ฒƒ— ˜. ทธฆฌณ , operator=˜ ฆฌํ„ดํ˜•„ ณดฉด String— Œ€ํ•œ  ˆํŸฐŠค Œ คธฐ •Œฌธ— ฆฌํ„ดํ˜•ด ˜ํ•˜€ •ŠฒŒ œ‹ค. ทธž˜„œ, error ฐœƒ‹œํ‚จ‹ค. งŒ•ฝ error ฐœƒ ‹œํ‚ค€ •ŠŠ”‹คฉด, operator=ด ํ˜ธถœ˜Š” ธก—„œ  œณตœ ธž€ •„‹ˆ ปดํŒŒŸฌ€ ฐœƒ‹œํ‚จ ž„‹œ €ˆ˜งŒ ˆ˜ •œ‹คŠ” ฒƒ— †€ž„ฒƒด‹ค. --;

..
ฒฐก „ –˜ธฐ ํ•˜žฉด, ˜ํ™˜˜ ™ชฝ €„— Œ€ํ•œ  ˆํŸฐŠค *this ˜Œ ค „ก ˜ํ™˜ —ฐ‚ฐž „ –ธํ•ด• ํ•œ‹ค. งŒ ด™ธ˜ „ ํ•˜ฉด, —ฐ† ธ ˜ํ™˜„ ํ•  ˆ˜ —†ฒŒ ˜ณ , ํดž˜Šค ‚ฌšฉํ•˜Š” ฝ”“œ—„œ˜ ฌต‹œ ธ ํƒ€ž… €ํ™˜„ ํ•  ˆ˜ —†ฒŒ œ‹ค.

3.6. Item 16: Assign to all data members in operator=

operator= —ฐ‚ฐž ˆ˜ํ–‰ํ• •Œ ฐœฒด ‚ด ฐฐ˜ ชจ“  ฐดํ„ฉค„ ˜ํ™˜ํ•  ํ•„š”€ žˆ‹คŠ” –˜ธฐ.



ƒ†˜ ฒฝšฐ ํŠํžˆ‚˜ กฐ‹ฌํ•ด„œ operator= —ฐ‚ฐž งŒ“ค–ด ค˜• ํ•œ‹ค.
~cpp 
class Base {
public:
  Base(int initialValue = 0): x(initialValue) {}
private:
  int x;
};
class Derived: public Base {
public:
  Derived(int initialValue)
  : Base(initialValue), y(initialValue)   {}
  Derived& operator=(const Derived& rhs);
private:
  int y;
};

// The logical way to write Derived's assignment operator is like this 
// erroneous assignment operator
Derived& Derived::operator=(const Derived& rhs)
{
  if (this == &rhs) return *this;    
  
  y = rhs.y;                         // assign to Derived's
                                     // lone data member
  return *this;                      // see Item 15
}

// Unfortunately, this is incorrect, because the data member x in 
// the Base part of a Derived object is unaffected by this assignment operator. 
// For example, consider this code fragment 
void assignmentTester()
{
  Derived d1(0);                      // d1.x = 0, d1.y = 0
  Derived d2(1);                      // d2.x = 1, d2.y = 1
  d1 = d2;			 // d1.x = 0, d1.y = 1!
}
ณดธฐ™€ ฐ™ด  œŒ€กœ ž‘™ํ•˜€ •ŠŠ” operator= —ฐ‚ฐžด‹ค. ทธŸ, ดฒƒ„ –ด–ปฒŒ ณ ˜ฉด ข‹„Œ? ด ฌธ œ ํ•ดฒฐํ•˜ธฐ œ„ํ•ด„œŠ”, ‹คŒ ฐ™ด Baseํดž˜Šค˜ operator=—ฐ‚ฐž ํ˜ธถœํ•ด ฉด œ‹ค. ( Derived ํดž˜Šค˜ operator= —ฐ‚ฐž—„œ x ˜ํ™˜ํ•ด €‹คŠ” ฒƒ€ ํ—ˆšฉ˜€ •Šธฐ •Œฌธ—.)
~cpp 
// correct assignment operator
Derived& Derived::operator=(const Derived& rhs)
{
  if (this == &rhs) return *this;
  Base::operator=(rhs);    // call this->Base::operator=
  y = rhs.y;
  return *this;
}


ƒ† € จํ•˜—ฌ œ ‚ฌํ•œ ฌธ œ€ ณต‚ฌ ƒ„ž—„œ„ ƒธธ ˆ˜ žˆ‹ค. ฐ‘˜ ฝ”“œ ณดž.
~cpp 
class Base {
public:
  Base(int initialValue = 0): x(initialValue) {}
  Base(const Base& rhs): x(rhs.x) {}
private:
  int x;
};
class Derived: public Base {
public:
  Derived(int initialValue)
  :  Base(initialValue), y(initialValue) {}
  Derived(const Derived& rhs)      // erroneous copy
  : y(rhs.y) {}                    // constructor
private:
  int y;
};
Derived ํดž˜Šค˜ ณต‚ฌ ƒ„ž ณดฉด Baseํดž˜Šค˜ ฉค„ €ˆ˜Š” ดˆธฐํ™” ‹œํ‚ค€ •ŠŒ„ •Œˆ˜ žˆ‹ค. ดŸฐ ฌธ œ ํ”ํ•˜ธฐ œ„ํ•ด„œŠ” ฐ‘˜ ฝ”“œ™€ ฐ™ด Baseํดž˜Šค˜ ณต‚ฌ ƒ„ž ํ˜ธถœํ•ด ฉด œ‹ค.
~cpp 
class Derived: public Base {
public:
  Derived(const Derived& rhs): Base(rhs), y(rhs.y) {}
  ...
};
ด   Derivedํดž˜Šค˜ ณต‚ฌƒ„ž ํ˜ธถœํ•ด„ Baseํดž˜Šค˜ ฉค„ €ˆ˜—ญ‹œ ž˜ ณต‚ฌ œ‹ค.

3.7. Item 17: Check for assignment to self in operator=

assignment to self in operator= (žฌ€˜ํ™˜) Š” ‹คŒ ฐ™„•Œ ฐœƒํ•œ‹ค.
~cpp 
class X { ... };
X a;
a = a;                     // a is assigned to itself
'™œ ดŸฐ Œ€ž…„ ํ•˜Š”€. ํ”„กœทธžจ งœŠ” †ˆด ฐ”ณด ธ€?' Š” ƒฐ„ ํ•  ˆ˜ „žˆ€งŒ, ฐ‘˜ ฝ”“œ€ žˆ‹คณ  ํ•˜ž.
~cpp 
a = b
ทธŸฐฐ b€ aกœ ดˆธฐํ™”œ  ˆํŸฐŠคฉด ณดธฐ—Š” žฌ€˜ํ™˜— ํ•ด‹ํ•œ‹ค. ดŸฐ €Šฅํ•œ ƒํ™ฉ— Œ€ฒ˜ํ•˜ธฐ œ„ํ•ด ํŠ„ํžˆ ˜ €€Š” ฒƒ— Š” ‘€€ ข‹€  ด žˆ‹ค. ฒซงธŠ” ํšจœจ„ด‹ค. ˜ํ™˜ —ฐ‚ฐž˜ ƒœ„ €„—„œ žฌ€˜ํ™˜„ €‚ฌํ•  ˆ˜ žˆ‹คฉด, ฐ”กœ ฆฌํ„ดํ•  ˆ˜ žˆธฐ •Œฌธด‹ค. ‘ฒˆงธŠ”,  •ํ™•ํ•จ„ ํ™•ธํ•˜Š” ฒƒด‹ค. ฐ˜ œกœ ˜ํ™˜ —ฐ‚ฐžŠ” ฐฒด˜ ƒˆกœšด ฐ’— ํ•ด‹ํ•˜Š” ƒˆกœšด ฆฌ†ŒŠค“ค„ ํ• ‹ํ•˜ธฐ  „— ฐฒด— ํ• ‹œ ฆฌ†ŒŠค“ค„ ํ•ด œํ•ด•งŒ ํ•œ‹ค. ด „ ฐ’“ค„  œฐํ•ด• ํ•œ‹คŠ” งด‹ค. žฌ€˜ํ™˜ ฒฝšฐ ดŸฐ‹œกœ ด „ ฐ’“ค„  œฐํ• ฒฝšฐ ํฐ hazard € ธ ˜จ‹ค. ™œƒํ•˜ฉด, ธฐกด ฆฌ†ŒŠค“คด ƒˆกœšด ฆฌ†Œ“ค„ ˜ํ™˜ํ•˜Š”  •—„œ ํ•„š”ํ•˜ฒŒ   ˆ˜ žˆธฐ •Œฌธด‹ค.




String ฐฒด“ค˜ ˜ํ™˜„ ƒฐํ•ด ณดž. —ฌธฐ—„  žฌ€˜ํ™˜„ €‚ฌํ•˜€ •Šณ  žˆ‹ค.
~cpp 
class String {
public:
  String(const char *value);    // see Item 11 for
                                // function definition
  ~String();                    // see Item 11 for
                                // function definition
  ...
  String& operator=(const String& rhs);
private:
  char *data;
};

// an assignment operator that omits a check
// for assignment to self
String& String::operator=(const String& rhs)
{
  delete [] data;    // delete old memory

  // allocate new memory and copy rhs's value into it
  data =   new char[strlen(rhs.data) + 1];
  strcpy(data, rhs.data);
  return *this;      // see Item 15
}
ทธฆฌณ , ด™€ ฐ™€ ฒฝšฐ ณดž.
~cpp 
String a = "Hello";

a = a;               // same as a.operator=(a)
Stringฐฒด˜ operator= —ฐ‚ฐž •Œ *this™€ rhsŠ” ‹คฅธฒƒ ฒ˜Ÿ ณดด€งŒ, ด ‘˜€ ฐ™€ ฐดํ„ pointingํ•˜ณ  žˆ‹ค. (ฐ™€ ฐฒดดธฐ •Œฌธ—..)



˜ํ™˜ —ฐ‚ฐž€ ˆ˜ํ–‰ํ•˜Š” ฒซ ฒˆงธ ž‘—…ด data ‚ญ œํ•˜Š” ฒƒดฉฐ, ฒฐŠ” ‹คŒ ฐ™‹ค.





ด œ ˜ํ™˜—ฐ‚ฐž—„œ strcpy ˆ˜ํ–‰ํ• •Œ ฐœƒํ•˜Š” € ˜ˆธกํ•  ˆ˜ —†ฒŒ ˜—ˆ‹ค. ดฒƒ€ data€ ‚ญ œ˜ฉด„œ rhs.data€ ‚ญ œ˜—ˆธฐ •Œฌธด‹ค. ดฒƒ€ data, this->data ทธฆฌณ , rhs.data€ ชจ‘ ฐ™€ ํฌธํ„ธฐ •Œฌธ— ทธ ‡ฒŒ œฒƒด‹ค. ตœ•…˜ ƒํ™ฉด‹ค..


ด œ ™œ? žฌ€˜ํ™˜„ €‚ฌํ•ด• ํ•˜Š”€ •Œ•˜„ ฒƒด‹ค.




ทธŸ, –ด–ค‹œกœ žฌ€˜ํ™˜ธ€ •„‹Œ€ €‚ฌํ• Œ? ข…ฅ˜Š” ‹ค–‘ํ•˜‹ค.
~cpp 
// data˜ ™„„ €‚ฌ
String& String::operator=(const String& rhs)
{
  if (strcmp(data, rhs.data) == 0) return *this;
  ...
}

// ฐฒด˜ ฉค„ €ˆ˜“ค˜ ฐ’ด ™ํ•œ€ €‚ฌ
// ด•Œ operator== „ ‹ค‹œ žฌ •˜ ํ•ด–ด• ํ•œ‹ค
C& C::operator=(const C& rhs)
{
  // check for assignment to self
  if (*this == rhs)              // assumes op== exists
    return *this;
  ...
}

// †Œฐ’„ ํ†ตํ•œ €‚ฌ - €žฅ ข‹€ ํšจ ธฐŒ€ํ• งŒ ํ•˜‹ค.
C& C::operator=(const C& rhs)
{
  // check for assignment to self
  if (this == &rhs) return *this;
  ...
}

// ํดž˜Šคงˆ‹ค ‹„ž ‘–ด €‚ฌํ•˜Š” ฐฉฒ•
// ดฒฝšฐ—„ operator == „  •˜ํ•˜—ฌ ‹„ž€ ฐ™€€ €‚ฌํ•ดณด•„• ํ•œ‹ค.
class C {
public:
  ObjectID identity() const;            // see also Item 36
  ...
};

4. Classes and Functions: Design and Declaration

ํšจ ธ ํดž˜Šค „„ž€ ฌด—‡ธ€? ‹คฃจŠ” €„

1. ฐฒด“คด –ด–ปฒŒ ƒ„˜ณ  †Œฉธ  ฒƒธ€?

2. ฐฒด ดˆธฐํ™”™€ ฐฒด ˜ํ™˜ด –ดŠ  •„ ฐจด€ ‚˜Š”€?

3. ƒˆกœšด ํƒ€ž…˜ ฐฒด ฐ’— ˜ํ•ด  „‹ฌํ•˜Š” ฒƒ€ ฌด—‡„ ˜ธ ํ•˜Š”€?

4. ƒˆกœšด ํƒ€ž…˜ ฐฒด€ ƒ† ทธž˜ํ”„— งžŠ”€?

5. –ด–ค ข…ฅ˜˜ ํƒ€ž… €ํ™˜ด ํ—ˆšฉ˜Š”€?

6. –ด–ค —ฐ‚ฐž™€ ํ•จˆ˜€ ƒˆกœšด ํƒ€ž…„ œ„ํ•ด  ‹ํ•œ€?

7.  ‘ —ฐ‚ฐž(public, protected, private) –ด–ปฒŒ  šฉํ•  ฒƒธ€?

8. etc..

4.1. Item 18. ตœ†Œํ•œ˜ ™„ „ํ•œ ํดž˜Šค ธํ„ฐํŽ˜ดŠค ถ”ตฌํ•œ‹ค.

interface? ํดž˜Šค ดšฉํ•˜Š” ํ”„กœทธž˜จธ€  ‘ํ• ˆ˜ žˆŠ” ˆ˜‹จ„ Š” ฒƒด‹ค. ฐ˜ œกœ ํ•จˆ˜“คงŒ ดŸฌํ•œ ธํ„ฐํŽ˜ดŠค ‚ด— กดžฌํ•œ‹ค. งŒ•ฝ ํดž˜Šค‚ด˜ ฐดํƒ€ €“ค—ฒŒ  ‘„ ํ—ˆšฉํ•˜ฒŒ ˜ฉด งŽ€ ‹จ “คด ƒธฐธฐ •Œฌธด‹ค. („กœ Š€Š” ชปํ•ด ดค‹ค.. ^^;)

ตœ†Œํ•œ˜ ™„ „ํ•œ ํดž˜Šค ธํ„ฐํŽ˜ดŠค ถ”ตฌํ•œ‹ค(?) ดง€ ํดž˜Šค‚ด— ตฐ””ธฐ ฆ‰ „Šทํ•œ „ ํ•˜Š” ฉค„ ํ•จˆ˜€ กดžฌ ํ•˜€ •ŠŠ”‹คŠ” ˜„ œ‹ค. ทธฆฌณ , ทธ ํดž˜ŠคŠ” ทธงŒํ ณตžกํ•˜€•Š„ ฒƒด‹ค. ทธฆฌณ , ตœ†Œํ•œ˜ ธํ„ฐํŽ˜ดŠคกœ ด ํดž˜Šค ‚ฌšฉํ•˜Š” ‚ฌšฉž€ ชจ“  (?)„ ํ• ˆ˜€ žˆ–ด•ํ•œ‹ค.

ทธŸฐฐ, ™œ ตœ†Œํ•œธ€? —ฌŸฌ€€ „ ํ• ˆ˜ žˆŠ” ฉค„ ํ•จˆ˜“ค„ „† ถ”€ํ•ด ‚˜€ฉด •ˆ˜Š” ฒƒธ€? Œ€‹ต€ •ˆœ‹ค. ™œ •ˆ˜Š” ฒƒŒ? ‹‹ € ฉค„ ํ•จˆ˜€ 10ฐœ žˆŠ” ํดž˜Šค™€ 100ฐœ€ žˆŠ” ํดž˜Šคค‘ –ด–คฒƒด ดํ•ดํ•˜ธฐ ‰ฝ‹คณ  ƒฐํ•˜Š”€? ‚˜ งŒ “ฐ คŠ” ํดž˜Šค€ •„‹Œดƒ ‹คฅธ ‚ฌšฉž“คด ‰ฝฒŒ ดํ•ด ํ• ˆ˜ žˆ„ก งŒ“ค–ด• ํ•˜€ •Šฒ Š”€? ทธ ‡ธฐ •Œฌธ— ตœ†Œํ•œ˜ ธํ„ฐํŽ˜ดŠค ถ”ตฌํ•˜Š” ฒƒด‹ค. ทธฆฌณ , €ฆฌ ธ ฉด—„œ •Œ  € ํ•จˆ˜“ค„ €„ ํดž˜Šค€ šฉดํ•˜‹คŠ” ฒƒด‹ค. ค‘ณตœ ฝ”“œ˜€ •„‹ˆฉด ฐœ„ ํ•  ฒƒ“ค„ ํ–ฅํ›„— ํ•˜ธฐ ‰ฝ‹คŠ” ฒƒด‹ค. ˜ํ•œ, document ž‘„ํ•œ‹ค “ € ํ• •Œ  € ฉค„ ํ•จˆ˜“ค„ €„ ํดž˜Šค ชฝด šฉดํ•˜‹คŠ” ฒƒด‹ค. งˆ€ง‰œกœ •„ ธด ํดž˜Šค  •˜Š” ธด ํ—ค” ํŒŒ„ ดˆž˜ ํ•œ‹ค. ฐ˜ œกœ ํ—ค” ํŒŒ“ค€ ํ”„กœทธžจด ปดํŒŒ  •Œงˆ‹ค งค ฒˆ ฝํ˜€ ธ• ํ•˜ธฐ •Œฌธ— ํ•„š” ดƒ ธด ํดž˜Šค  •˜Š” ํ”„กœ ํŠธ ธฐ ค‘˜ ด ปดํŒŒ ‹œ„„ ฐ‰•„ Š”‹ค. ทธŸฐ ดœ “ค •Œฌธ— ตœ†Œํ•œ˜ ํดž˜Šค ธํ„ฐํŽ˜ดŠค ถ”ตฌํ•˜Š” ฒƒด €” ‚˜€ ํŒ‹จดŠ” ฒƒด‹ค.

4.2. Item 19. ฉค„ ํ•จˆ˜, „ฉค„ ํ•จˆ˜ ฐ ํ”„ Œ“œ ํ•จˆ˜ ตฌ„ํ•œ‹ค.

Œ€ฒŒ class‚ด— operator —ฐ‚ฐž ‚ฌšฉํ•จœกœ„œ €” ํŽธํ•œ code(?)Š” ฒƒ„ ํ•˜ธฐ œ„ํ•ด„œ „ –ธ ํ•˜Š” ํ•จˆ˜“คด ฉค„ ํ•จˆ˜—ฌ• ํ•˜Š”€ •„‹ˆฉด friendํ•จˆ˜—ฌ• ํ•˜Š”€
‘ฅ• ‘ฅ• ํ•˜Š” ฒƒด‹ค. ฉค„ €ˆ˜“ค˜ —ฐ‚ฐ„ ‹ค–‘ํ•˜ฒŒ  šฉ‹œํ‚คณ  ‹ถ‹คฉด friend ํ•จˆ˜ จ„œ ฐ˜ ƒˆ˜€ ํดž˜Šค ธŠคํ„Šค˜ ™ํŽธ— žฆฌ žกณ  žˆ–ด„ —ฐ‚ฐด ˜ฒŒ ํ•˜ณ ‹ถ‹คŠ” ƒฐ„ €€ณ  žˆœฉด friendํ•จˆ˜ จ„œ „ ฉค„ ํ•จˆ˜ งŒ“ค–ด ทธ —ฐ‚ฐ„ €›ํ•˜Š” –˜ธฐ ด‹ค.
~cpp 
Num a(10);
int temp;
temp = 2 * a; // ดŸฐ —ฐ‚ฐ. - friendํ•จˆ˜ ‚ฌšฉํ•˜—ฌ —ฐ‚ฐž  •˜ ํ•ดค˜•€งŒ ž‘™ํ•œ‹ค.
ทธ ‡€งŒ, ดŸฐ —ฐ‚ฐž“ค„ ˜ •ˆ“ฐŠ” ฒƒฐ™‹ค.. ใ…กใ…ก; ‚˜„ friendํ•จˆ˜ จณธ ด —†‹ค.. ใ…กใ…ก; ํ•™ต ‹œํ—˜—„œ ‚˜˜ฌฒ•ํ•œ –˜ธฐ“ค.


- tip -

—ฌธฐ„œ fŠ”   ˆํžˆ „ –ธํ•˜ณ ž ํ•˜Š” ํ•จˆ˜ ‚˜ํƒ€‚ดณ  CŠ” ฐœ… œกœ € จžˆŠ” ํดž˜Šค ˜ธํ•œ‹ค.
  • operator>>™€ operator<<Š” ฒฐฝ” ฉค„€  ˆ˜ —†‹ค. งŒ f€ operator>>˜Š” operator<<์ด๋ผ๋ฉด, f๋ฅผ ๋น„๋ฉค๋ฒ„ ํ•จ์ˆ˜๋กœ ๋งŒ๋“ ๋‹ค. ๊ฒŒ๋‹ค๊ฐ€ f๊ฐ€ C์˜ ๋น„๊ณต์šฉ ๋ฉค๋ฒ„๋กœ ์ ‘๊ทผ์ด ์š”๊ตฌ๋œ๋‹ค๋ฉด f๋ฅผ C์˜ ํ”„๋ Œ๋“œ๋กœ ๋งŒ๋“ ๋‹ค.
  • „ฉค„ ํ•จˆ˜“คงŒ ทธ“ค˜ €žฅ ™ชฝํŽธ— žˆŠ” ธž—„œ ํƒ€ž… €ํ™˜ด –ด‚œ‹ค. งŒ f€ €žฅ ™ชฝํŽธ— žˆŠ” ธž—„œ ํƒ€ž… €ํ™˜„ ํ•„š”กœ ํ•œ‹คฉด f „ฉค„ ํ•จˆ˜กœ งŒ“ ‹ค. ฒŒ‹ค€ f€ C˜ „ณตšฉ ฉค„—  ‘ด ํ•„š”ํ•˜‹คฉด f C˜ ํ”„ Œ“œกœ งŒ“ ‹ค.
  • ทธ ฐ–— ชจ“  ฒƒ€ ฉค„ ํ•จˆ˜ด–ด• ํ•œ‹ค. ดƒ˜ –ด–ค ฒƒ—„ ํ•ด‹˜€ •Šœฉด f C˜ ฉค„ ํ•จˆ˜กœ งŒ“ ‹ค.

4.3. Item 20. ฐดํ„ฉค„ ณตšฉ(public) ธํ„ฐํŽ˜ดŠค— ํฌํ•จ‹œํ‚ค€ •ŠŠ”‹ค.

 œชฉทธŒ€กœ.

4.4. Item 21. €Šฅํ•œ const ดšฉํ•œ‹ค.

const “ฐŠ” ดœ Š” š”†ˆ˜ ฐ’€  ˆŒ€กœ €ํ•˜€ ง•„• ํ•œ‹คŠ”ฒƒ„ ณด—ฌธฐ œ„ํ•จดž„Œ? •„ฌดํŠ constกœ € •„ ํ•ด†“œฉด –ด–ปฒŒ ํ•˜“  ทธ ฐ’€  ˆŒ€กœ €ํ•˜€ •ŠŠ” ‹คŠ”ฒƒ€ ณดžฅด œ‹ค.
~cpp 
const char *p = "Hello";
char * const p = "Hello";
const char * const p = "Hello"; 
// ด „€€˜ ฐจด € ญ˜Œš”?
// ž˜ ƒฐ ํ•˜ฉด •Œˆ˜ žˆ„ —š”.
// pointerž€ €ฆฌํ‚คŠ” ณณ˜ ฐ’, †Œกœ ดฃจ–ด „ †ˆด‹ˆŒ.
// –ด–ค•ŒŠ” †Œ€ €ํ•˜€ ง•˜œฉด ํ• •Œดณ ,
// –ด–ค†ˆ€ €ฆฌํ‚คŠ” ณณ˜ ฐ’ด €ํ•˜€ ง•˜œฉด ํ• •Œ.. ดŸฐ ‹œกœ ƒฐํ•˜ฉด ‰ฌšธ“ ํ•˜„š”.. ใ…Žใ…Ž
.. ถ”ํ›„—  •ฆฌ..

4.5. ํ•ญชฉ 22. ฐ’— ˜ํ•œ ํ˜ธถœณด‹คŠ”  ˆํŸฐŠค— ˜ํ•œ ํ˜ธถœ„ „ ํ˜ธํ•œ‹ค.

ด ํ•ญชฉ€ ฐธกฐ œ šฉํ•˜ฒŒ ‚ฌšฉํ•  ˆ˜ žˆŠ” ฒฝšฐด‹ค.
ฒซฒˆงธŠ” ํ•จˆ˜˜ ฆฌํ„ฐ’œกœ ‚ฌšฉ‹œ ฌดฆฌํ•˜ฒŒ ž„‹œฐฒด€ ƒ„ด   ˆ˜ žˆ‹ค.
{{|
class Person
{
...
private:
string name, address;
}
class Student : public Person
{
...
private:
string schoolName, schoolAddress;
}
|}}
ด ‡ฒŒ ํดž˜Šค€ กดžฌํ•˜Š” ฒฝšฐ
{{|
Student returnStudent(Student s)
{
return s;
}

...

Student plato;

returnStudent(plato);
|}}
ด ‡ฒŒ ํ˜ธถœด œ‹คฉด

platoŠ” returnStudentํ•จˆ˜—„œ ธžกœ „˜–ด€ฉด„œ ž„‹œฐฒด งŒ“คฒŒ ˜ณ  ํ•จˆ˜ ‚ด— “ฐดฉด„œ sกœ ˜ ํ•œฒˆ ƒ„˜ณ  ํ•จˆ˜€ ํ˜ธถœด ˜ณ  ฐ˜ํ™˜  •Œ ฐ˜ํ™˜œ ฐฒด œ„ํ•ด ˜ ํ•œฒˆ ณต‚ฌ ƒ„ž€ ํ˜ธถœœ‹ค.
ด 3ฒˆ˜ €€ ธ ํ˜ธถœด –ด‚˜ฉด„œ ฉค„ธ string“ค€ ด 12ฒˆด‚˜ ƒ„ด˜ณ  ํŒŒดด€ œ‹ค.

‘ฒˆงธŠ” ž˜€Š” ฌธ œ(slicing problem)กœ œ„˜ ˜ˆ—„œ returnStudentํ•จˆ˜— ธžกœ Personํ˜• ฐฒด€ ‹คšด บŠคํŒ…ํ•ด„œ “ค–ด€Š” ฒฝšฐ ‚ด€ ธ ž„‹œฐฒด“ค˜ ƒ„œกœ Studentํ˜• ฐฒดกœ ธ‹˜ Studentํ˜• ฐฒดงŒ˜ ฉค„ ํ˜ธถœํ•˜ฒŒ˜ฉด  •ƒž‘™„ ณดžฅํ•  ˆ˜ —†ฒŒ œ‹ค.

4.6. ํ•ญชฉ 23. ฐฒด ฐ˜ํ™˜‹œ  ˆํŸฐŠค ฐ˜ํ™˜ํ•˜€ •ŠŠ”‹ค.

ฐฒด ฐ˜ํ™˜€ ฐ’˜ ˜ํ•œ ํ˜ธถœด ฐธกฐณด‹ค ํ›จ”ฌ „‹จํ•˜ณ  ช…ํ™•ํ•˜‹ค.
ทธ ‡€ •Šณ  ฐธกฐ— ˜ํ•œ ํ˜ธถœ„ ํ•  ฒฝšฐ— …—„œŠ” ‚ด€ ž„‹œฐฒด ํ†ตํ•ด ฐ˜ํ™˜„ ํ•˜ คณ  ํ• • ทธ ž„‹œ ฐฒด˜ ฉ”ชจฆฌŠ” Šคํƒ— žˆธฐ •Œฌธ— ฌธ œ€ ˜ณ , new ‚ฌšฉํ•ด„œ ํž™ ธฐฐ˜œกœ งŒ“ค•ŒŠ” —ฐ‹ฌ— „ฒˆ˜ ํ˜ธถœด žˆ„ ฒฝšฐ ํ•„—ฐ œกœ ฉ”ชจฆฌ€ ˆ„ถœœ‹ค. ทธ ‡‹คณ  static˜  •  ฐฒด˜ ฒฝšฐ—„ „ตฌธ(operator =)—„œ ‚ฌšฉœ‹คฉด –ธ œ€ ฐธœกœ „‚ฐด  ฒƒด‹ค. ทธ ‡‹คณ   •  ฐฒด ฐฐ—ดกœ ฌดฆฌํ•ด„œ ตฌํ˜„„ ํ•˜ณ ž ํ•œ‹คฉด ทธฐ”กœ ‚ฝงˆด‹ค.

4.7. ํ•ญชฉ 24. ํ•จˆ˜ ˜ค„กœ”ฉ ””ํดํŠธ ธžฐ’ ค‘—„œ ˜ŠฒŒ „ ํƒํ•œ‹ค.

  • std::numeric_limits<TYPE>::min(); // ํ—ค” <limits> TYPE˜ ตœ†Œฐ’„ ตฌํ•ด€‹ค. INT_MIN ฐ™€ ฐ’.

””ํดํŠธ ธžฐ’„ ‚ฌšฉํ•  ˆ˜ žˆŠ” ฒฝšฐ„ žˆณ  —†Š” ฒฝšฐ„ žˆ‹ค.
˜ˆ “คฉด 5ฐœ˜ ฐ’˜ ํ‰ท „ ‚ธ‹ค˜€ ํ•˜Š” ฒฝšฐŠ” ””ํดํŠธ ธž ‚ฌšฉํ•  ˆ˜ —†‹ค.

ž‹ ด •Œ•„„œ ƒํ™ฉ— ”ฐ ฒ˜‹ ํ•˜„ก.

4.8. ํ•ญชฉ 25. ํฌธํ„‚˜ ˆ˜˜ํ˜• ํƒ€ž…ƒ˜ ˜ค„กœ”ฉ„ ํ”ํ•œ‹ค.

งŒ•ฝ ‹คŒ ฐ™€ ฒฝšฐ
{{|
void f(string *);
f(int);
..
f(0); //  •ˆ˜ํ˜• 0ด€กœ f(int)€ ํ˜ธถœ
f(NULL); // ?-_-? ต‰žฅํžˆ ณตžก ฌ˜ํ•˜‹ค-_-; „ –ธ— ”ฐ„œ 0ด  ˆ˜„ (void*)0ด  ˆ˜„ 0Lด  ˆ˜„ ““˜ ฒฝšฐ€ žˆ‹ค.
|}}
NULLดŠ” ƒˆ˜— Œ€ํ•œ ํƒ€ž…˜  •˜€ ชจํ˜ธํ•˜‹ค.

ดŸฐ ฒฝšฐ ‹คŒ ฐ™€ ฐฉฒ•ด žˆ‹ค.
{{|
const class // ํดž˜Šค˜ ด„ด ํ•„š”ํ•˜€ •Š‹ค.
{
public:
template<class T> operator T*() const // ชจ“  NULL ํฌธํ„ Œ€ฒดํ•œ‹ค.
{
return 0;
}
template
{
return 0;
}
private:
void operator&() const; // NULL˜ †Œฐ’ดž€ กดžฌํ•˜€ •ŠŠ”‹ค.
} NULL;
|}}
ฒฐก € ˜„กดฉด ด ‡ฒŒ ณตžกํ•˜ฒŒ “ค–ด€Š” ฒฝšฐ งŒ“ค€ •Šœฉด œ‹ค.

4.9. ํ•ญชฉ 26. ž žฌ  ชจํ˜ธ„„ ฒฝ„ํ•œ‹ค.

  • ˆ„ตฌ‚˜ ‚˜„Œ€กœ˜ ฒ ํ•™„ € ธ• ํ•œ‹ค. –ด–ค ดŠ” ถˆ„„˜ ฒฝ œํ•™„ ณ  –ด–ค ดŠ” œคํšŒ„„ Š”‹ค. ˜ –ด–ค ดŠ” COBOLด „งœ ํ”„กœทธž˜ฐ –ธ–ดณ  Š”‹ค. C++„ ‚˜„˜ ฒ ํ•™„ €€ณ  žˆ‹ค. C++Š” ž žฌ ธ • งคชจํ˜ธ„€ —Ÿฌ€ •„‹ˆณ  ƒฐํ•œ‹ค. ‚˜Š” ํ•™-ธฐˆ  „œ —„œ„ ดŸฌํ•œ ถฉ„ํžˆ Š€ ƒฐ˜ ด•ธฐ„ ํ•„š”ํ•˜‹คณ  ƒฐํ•œ‹ค.

C++–ธ–ดŠ” ž žฌ €ธ • งคชจํ˜ธ„„ €„ –ธ–ดด‹ค.
…—„œŠ” ช‡€€ ˜ˆ “คณ  žˆ‹ค.
{{|
void f(A);

...

B b;
f(b);
|}}
ํ˜ธถœ‹œ ํ•จˆ˜ fŠ” ธžกœ A š”ตฌํ•œ‹ค. šฐ„  B€ A˜ ž‹ด‚˜ €ชจธ€ ํ™•ธ ํ•ดํ…Œณ  operator A() ฐพ•„ €„ ชจฅธ‹ค.
งŒ•ฝ ด ‘ฐœ€ งŒํ•˜Š” Bฉด • งคชจํ˜ธ„˜ ฒฝšฐด‹ค. (ดŸฐ ฒฝšฐŠ” งŒ“คฉด •ˆ ณ  ƒฐํ•œ‹ค.)

{{|
void f(int);
void f(char);

...

double d=6.02;
f(d)
|}}
€žฅ ‰ฝฒŒ  ‘ํ•  ˆ˜ žˆŠ” • งคชจํ˜ธํ•œ ฒฝšฐด‹ค.
ด ฒฝšฐŠ” static_cast<TYPE> ํ†ตํ•ด ‰ฝฒŒ ํ•ดฒฐ €Šฅํ•˜‹ค.

{{|
class Base1
{
public:
int doIt();
}
class Base2
{
public:
int doIt();
}
class Derived : public Base1, public Base2
{
}

...

Derived d;
d.doIt();
|}}
Œ€ํ‘œ ธ ‹คค‘ƒ†˜ • งคชจํ˜ธ„ด‹ค.
ดฒƒ ˜ํ•œ  ‘ฒ”œ„ „ •ํ•ด คŒœกœ ‰ฝฒŒ ํ•ดฒฐ €Šฅํ•˜‹ค. (d.Base1::doIt() ฐ™€ ฒฝšฐ)

ด™€ ฐ™€ ˜ˆ—„œ •Œˆ˜ žˆ“ด C++€ • งคชจํ˜ธ„„ ํ•˜‚˜˜ „งˆกœ ฐ›•„ “ค˜€‹คณ  ƒฐํ•œ‹ค.
ทธž˜„œ Œ€€„˜ ด™€ ฐ™€ ฒฝšฐ— ํ•ดฒฐํ•  ˆ˜ žˆŠ” œ —ฐ„ด žˆ‹ค.

4.10. ํ•ญชฉ 27. ˜„ํ•˜€ •Š€ ‚ด€ ƒ„ ฉค„ ํ•จˆ˜˜ ดšฉ„ ช…‹œ œกœ ง‰Š”‹ค.

œ„˜ ํ•ญชฉ—„œ ณด“ด C++€ • งคชจํ˜ธ„„ €‹ˆณ  žˆ‹ค.
”ฐ„œ ฝ””ฉƒ˜ —Ÿฌ œ„ํ—˜„„ ‚ฎถ”ธฐ œ„ํ•ด„œŠ” ตœŒ€ํ•œ ช…‹œ œกœ ํ•ดฒฐํ•  ˆ˜ žˆŠ” ฐฉ•ˆ„ „œฉด ข‹‹ค.

˜ˆกœ ˜ํ™˜—ฐ‚ฐž „ช…ํ•œ‹ค.
งŒ•ฝ C++˜ ํดž˜Šคกœ C –ธ–ด˜ ฐฐ—ด œ ‚ฌํ•œ ํดž˜Šค งŒ“คณ ž ํ•œ‹คฉด
C –ธ–ด˜ ฐฐ—ด œ ‚ฌํ•œ „งˆ„ €…€• ํ•œ‹ค.
C –ธ–ด—„œ ฐฐ—ด˜ ˜ํ™˜€ ถˆฒ•ด‹ค.
ทธŸฌ€กœ C++˜ ฐฐ—ดํดž˜Šค˜ ฒฝšฐ„ ˜ํ™˜—ฐ‚ฐž ฝ””ฉƒ˜ ถˆฒ•œกœ งŒ“คฉด ฐจํ›„ • งคชจํ˜ธํ•œ ด —†–ด„‹ค.
C++–ธ–ด ํดž˜Šค ธฐณธ ˜ํ™˜ —ฐ‚ฐž ฉค„˜ ณต‚ฌกœ  •˜˜–ด žˆœ€กœ
privateœกœ ˜ค„ด”ฉํ•˜ฉด   ˆํ•˜ฒŒ Œ€ฒ˜ํ•œ ฒฝšฐด‹ค.

4.11. ํ•ญชฉ 28.  „—ญ „ž„ŠคํŽ˜ดŠค „ํ• ํ•œ‹ค.

C++— “ค–ด˜คฉด„œ ‚ฌšฉœ „ž„ŠคํŽ˜ดŠคŠ” ํ›Œฅญํ•œ ชจ“ˆ€ฆฌฐฉฒ•ด‹ค.
•ฝ„˜ ถ”€ฝ””ฉœกœ งคšฐ ‰ฝฒŒ • งคชจํ˜ธ„„  œฐํ•œ‹ค.

5. ํดž˜Šค™€ ํ•จˆ˜ : ตฌํ˜„

5.1. ํ•ญชฉ 29. ‚ด€ ฐดํ„— Œ€ํ•œ "ํ•ธ“ค"„ ฆฌํ„ดํ•˜Š” ฒƒ„ ํ”ํ•ด.

‚ด€ ž›— Œ€ํ•œ ˆ˜ •/‚ญ œ€ €Šฅํ•˜„ก ฐ˜ํ™˜ํ•˜Š” ฒƒ€ ข‹€ ชปํ•œ ฐฉฒ•ด‹ค.

งŒ•ฝ ด™€ ฐ™€ ฒฝšฐ
{{|
class String
{
...

public:
operator char *() const;
private:
char *data;
}

...

String B("Hello World");
char *str = B;
strcpy(str, "Hi Mom");
|}}
String BŠ” ž›— Œ€ํ•œ ํ•ธ“ค„ „˜ฒจ€กœ ฉ”ชจฆฌ˜ œ ถœด ถˆ€ํ”ํ•˜‹ค.

C++ ํ‘œ€˜ String€ ฐ˜ํ™˜ฐ’„ constํ˜•œกœ ฐ˜ํ™˜ํ•˜Š” c_strฉค„ ํ•จˆ˜ ํ†ตํ•ด ด ํ”ํ•˜ณ  žˆ‹ค.
{{|
class String
{
...

public:
operator const char*() const;
}
|}}
ด™€ ฐ™ด ‚ฌšฉํ•œ‹คฉด ถฉ„ํžˆ œ„ํ—˜„ ํ”ํ•ดฐˆ ˆ˜ žˆ‹ค.

{{|
String someFamousAuthor()
{
return "E.H.Gombrich"; // the story of art˜  €ž
}

...

const char *pc = someFamousAuthor();
cout << pc;
|}}
ด™€ ฐ™ด ฐ˜ํ™˜ฐ’œกœ ‚ฌšฉ˜Š” ฒฝšฐ ž„‹œฐฒด€ ฐ˜ํ™˜˜ฉด„œ ํฌธํ„ „˜ฒจณ  ‚ญ œœ‹ค.
ทธ ‡ฒŒ ˜€กœ žƒ–ด„ฆฐ ํ•ธ“ค(dangle handle)งŒ ‚จฒŒ œ‹ค.

ปดํŒŒด œ‹คŠ”  —„œ • งคชจํ˜ธ„ณ  ํ• ˆ˜ žˆœ‚˜ ํ•ดฒฐํ•˜Š”ฐ „šฉด งŽด “ ‹ค.
(˜ํ™˜—ฐ‚ฐž—„œ const char*ํ˜•ํƒœ˜ ฐ˜ํ™˜ฐ’„ „˜ฒจ„•Œ ํ•ธ“ค— Œ€ํ•œ ž›„ ํ•˜‚˜ ” งŒ“ค–ด ฐ˜ํ™˜ํ•˜ฉด €Šฅ€ ํ•˜‹ค.)

‚ฌšฉ  „งˆ— ”ฐ„œ ํƒ€ํ˜‘;„ ํ•˜ž.

5.2. ํ•ญชฉ 30.  ‘ํ•˜ธฐ –ด คšด ฉค„— Œ€ํ•œ „ƒˆ˜ ํฌธํ„‚˜  ˆํŸฐŠค ฆฌํ„ดํ•˜Š” ฉค„ ํ•จˆ˜ ‚ฌšฉ„ ํ”ํ•˜.

ณธ ธ C++ ํดž˜Šค˜ กดžฌ˜ ดœ ด‹ค.
ํดž˜Šค˜ ฉค„Š” ด ‘ž˜ œป„ €€ณ  žˆ‹ค.
ด •Œ, ‚ดšฉด privateํ˜• ฐ™ด ‚ด€‚ฌšฉงŒ ํ—ˆฝํ•  ฒฝšฐ ด ‚ดšฉ„ ฐ˜ํ™˜ํ•˜Š” ํ˜•‹ด ‚˜˜คฉด •ˆœ‹ค.
(Stringํ˜• ฐ™ด C –ธ–ด˜ ํŠ„ ฐ˜“œ‹œ ํ˜ธํ™˜˜ฒŒ ํ•ด•ํ•  ฒฝšฐ กฐธˆ˜ ˜ˆ™ธณ  ƒฐํ•ด„ ข‹„“ ํ•˜‹ค;;)

5.3. ํ•ญชฉ 31. €—ญ ฐฒด— Œ€ํ•œ ฐธกฐ‚˜ ํ•จˆ˜ ‚ด—„œ new ดšฉํ•ด ดˆธฐํ™”œ ํฌธํ„ €ฆฌํ‚คŠ” ฐธกฐ ฆฌํ„ดํ•˜€ ง.

ดฒˆ ํ•ญชฉ€ •ž—„œ ช‡ฒˆ –ธธ‰ ˜—ˆ˜“ ํ•œฐ
{{|
class Rational
{
...

public:
friend const Rational& operator*(const Rational& lhs, const Rational& rhs)
{
Rational result(lhs.n*rhs.n, lhs.d,lhs.d);
return result;
}
private:
int n,d; // „ชจ™€ „žฐ’
}
|}}
ด™€ ฐ™€ ฒฝšฐ €—ญ ฐฒด resultŠ” ํ•จˆ˜˜ ฒ”œ„ ฒ—–ด‚˜ฉด„œ ‚ญ œœ‹ค.

{{|
class Rational
{
...

public:
friend const Rational& operator*(const Rational& lhs, const Rational& rhs)
{
Rational *result = new Rational(lhs.n*rhs.n, lhs.d,lhs.d);
return *result;
}
private:
int n,d; // „ชจ™€ „žฐ’
}
|}}
งŒ•ฝ ด™€ ฐ™„ ฒฝšฐ ํž™˜—ญ— ฉ”ชจฆฌ ƒ„ํ•˜ณ  ํ•จˆ˜˜ ฒ”œ„ ฒ—–ด‚˜”„ ‚ญ œ€ ˜€ •Š€งŒ
ค‘ณตœ operator *˜ ‚ฌšฉ‹œ ฉ”ชจฆฌ ˆ„ถœด ถˆ€ํ”ํ•˜‹ค.

ด ฌธ œ—„œŠ”  ˆํŸฐŠค€ •„‹Œ ฐ’œกœ ฐ˜ํ™˜ํ•จœกœ ํ•ดฒฐํ•  ˆ˜ žˆœ‚˜ „ˆฌด ํฐ „šฉด “ ‹ค.

  • ” ‚˜€ ฐฉฒ•„ •„‹œŠ” „€ ถ”€ํ•ด„š”;;

5.4. ํ•ญชฉ 32. €ˆ˜  •˜Š” €Šฅํ•œ ’คกœ Šฆถฐ.

C –ธ–ด ‚ฌšฉํ•  •ŒŠ” ํ•จˆ˜˜ ฒซจธฆฌ— €ˆ˜  •˜ํ•˜ณ  ‹œž‘ํ•˜˜€‹ค.
•„งˆ ดˆธฐ˜ C –ธ–ด—„œ €ˆ˜˜  •˜€ ฒซจธฆฌ— žˆ–ด• ํ•จ„ žˆ„ํ…Œณ  €ˆ˜ ‰ฝฒŒ ‹„ํ•˜ธฐ œ„ํ•ด„œ„ ‚ฌšฉœ ฐฉฒ•ด‹ค.
ดฒˆ ‚ดšฉ€  œชฉŒ€กœ €ˆ˜˜  •˜ €Šฅํ•œ Šฆถฐ„œ ‚ฌšฉ˜€ •Š„ ฒฝšฐ ถˆํ•„š”ํ•œ ž‘—…„ —†• ธฐ œ„ํ•จด‹ค.

{{|
string encryptedPassword(const string &password)
{
string encrypted;
if(password.length() < MINIMUM_PASS_LENGTH)
throw logic_error("password is too short");
encrypted = password;
encrypt(encrypted);
return encrypted;
}
|}}
ด™€ ฐ™€ ฒฝšฐ ˜ˆ™ธกœ „˜–ด€ฒŒ   ฒฝšฐ string encrypted; ฝ”“œŠ” “ธชจ€ —†‹ค.

{{|
string encryptedPassword(const string &password)
{
if(password.length() < MINIMUM_PASS_LENGTH)
throw logic_error("password is too short");

string encrypted(password);

encrypt(encrypted);
return encrypted;
}
|}}
ด ‡ฒŒ ณ ด ํ˜„ช…ํ•˜‹ค.

  • š”ฆ˜ ปดํŒŒŸฌŠ” Œ€ถฉ ด •„Š” •Œ•„„œ ํ•ด€ •Š‚˜š”?;;

5.5. ํ•ญชฉ 33. ธธ„ „ „ œกœ ‚ฌšฉํ•˜.

ธธ€ งคํฌกœณด‹ค ›ฐ–ด‚˜ณ  ‹คํ–‰†„ ฆ€ ‹œํ‚ฌˆ˜„ žˆœ‚˜ •Œ— ”ฐ ถ”€ ธ šฉŸ‰„ ƒ„ ‹œํ‚ฌˆ˜„ žˆ‹ค.
{{|
// "example.h" file
inline void f() { ... }

// "source1.cpp" file
#include "example.h"

// "source2.cpp" file
#include "example.h"
|}}
ด™€ ฐ™€ ฒฝšฐ ธธํ•จˆ˜ f source1.cpp™€ source2.cpp—„œ ฐฐ ƒ„‹œํ‚ฌˆ˜„ žˆ‹ค.
ดฒƒ งณ „ ธธ ํ•จˆ˜˜ ํ•จˆ˜ํฌธํ„ ทจํ•  •Œ ปดํŒŒŸฌ— ”ฐ ํŒŒงˆ‹ค  •  ณต‚ฌณธ„ ƒ„‹œํ‚ฌˆ˜„ žˆ‹ค.
ด ‡ฒŒ ถ”€ ธ šฉŸ‰ด Š˜–ด‚˜Š” ฒฝšฐ ™ธ—„ บ‹œ˜  ค‘ฅ „ ฐ†Œ‹œœ ˜คํžˆ ค „Šฅด ฐ†Œํ•  ˆ˜„ žˆ‹ค.

80-20 ํŒŒ ˆํ† ˜ „„— ”ฐ ค‘š”ํ•œ ฝ”“œŠ” •ฝ 20%€ ฐจ€ํ•œ‹คŠ” ฒƒ„ ƒฐํ•˜ณ  ค‘š”ํ•œ €„—งŒ ธธ ฒ˜ฆฌ ํ•ดž.

  • ƒ„ž™€ †ŒฉธžŠ” ธธœกœ ‚ฌšฉํ•ด„œŠ” •ˆœ‹ค. ดŠ” ปดํŒŒŸฌตฌํ˜„ž€ •Œ— ”ฐ ƒ„ž™€ †Œฉธž— ณดด€•ŠŠ” ฝ”“œ€„„ ํฌํ•จํ•  ˆ˜„ žˆธฐ •Œฌธด‹ค.

5.6. ํ•ญชฉ 34. ํŒŒ„˜ ปดํŒŒ ˜กด„(dependency)„ ตœ†Œํ™”ํ•˜.

ํŒŒ ํ•œ€„„ ˆ˜ •ํ•˜ณ  ‹ค‹œ ปดํŒŒ„ ‹œ„ ํ–ˆ„•Œ ชจ“  ํŒŒ„ ‹ค‹œ ปดํŒŒํ•˜ณ  งํฌํ•˜ณ  ‹คํ–‰ํ•˜Š” ฒฝํ—˜„ ํ•œฒˆ€ ํ•ดณด•˜œฆฌ ƒฐํ•œ‹ค.
ด™€ ฐ™ด ํŒŒ„˜ ˜กด„œกœ ธํ•ด „ˆฌด งŽ€ ปดํŒŒ ‹œ„„ žก•„Š”ฒƒ€ ‹œ„‚ญ„ดณ  ‚ฌžŒ— ”ฐ งคšฐ งœฆ‚˜Š” ด‹ค.
ดฒˆ ํ•ญชฉ€ ช‡€€ ฐฉฒ•œกœ ํŒŒ„˜ ˜กด„„ „ดŠ” ฐฉฒ•„  œ‹œํ•œ‹ค.

šฐ„  ํดž˜Šค˜  „ฐฉ ฐธกฐ „ช…ํ•œ‹ค.
 „ฐฉ ฐธกฐ ํ•จœกœ ํ—ค”€„—„œŠ” ™ธ€ ํดž˜Šค˜ ‚ดšฉ„ ‚ฌšฉํ•˜€ •Š•„ ” ดƒ˜ ฌด˜ธํ•œ ปดํŒŒ˜ —ฐฒฐณ ฆฌ Š„ˆ˜ žˆ‹ค.
ํ•˜€งŒ ƒํ™ฉ— ”ฐ„œŠ” ฐ˜“œ‹œ ํดž˜Šค˜ ‚ดšฉ„ ‚ฌšฉํ•ด•ํ•˜Š” ฒฝšฐ„ žˆณ  ทธŸด•ŒŠ”  „ฐฉ ฐธกฐ˜ ˜Š” •ฝํ•ด„‹ค.

ดŸด• Handleํดž˜Šค™€ ํ”„กœํ† ฝœ ํดž˜Šค ‚ฌšฉํ•œ‹ค.
Handleํดž˜ŠคŠ” ™ธ€—„œ ‚ฌšฉ  ‚ดšฉ˜ €„„ ”ฐกœ ––ด Handleํดž˜Šคกœ งŒ“ฌœกœ ตœ†Œํ•œ˜ ‚ดšฉ„ ํ—ค”— ํฌํ•จ‹œํ‚จ‹ค.
ํ”„กœํ† ฝœ ํดž˜ŠคŠ” ธํ„ฐํŽ˜ดŠค ‚ฌšฉํ•œ‹ค. ถ”ƒํ™”œ ธํ„ฐํŽ˜ดŠคงŒ งŒ“ค–ด ํ—ค”— ํฌํ•จ‹œํ‚คŠ” ฐฉฒ•œกœ ํŒŒ„˜ ˜กด„„ •ฝํ™”‹œํ‚จ‹ค.

6. ธŠคํ„Šค™€ ฐฒด€ํ–ฅ „„

6.1. ํ•ญชฉ 35. public „Šด "isa" ชจธงํ•˜„ก ํ•˜.

{{|
class Person
{
...
}
class Student : public Person
{
...
}
|}}
ด €„Š” public „Šธ "isa"€„ด‹ค.
ํ•˜€งŒ Person isa Studentด€ Student isa Personด •„‹˜„ ˜ํ•ด•ํ•œ‹ค.

ปดํ“จํ„Š” 0 1กœ ดฃจ–ด„ ณ ฒ ด‹ค. šฐฆฌ€ ƒฐํ•˜Š” ฒƒ„ ฐ”กœ ํ‘œํ˜„ํ•˜€ ชปํ•œ‹ค.
šฐฆฌ€ ˆ˜ํ•™„ ํฌํ•จํ•œ ‹คฅธ €„“ค—„œ ตํžŒ ง€ด ฐ”กœ  šฉ˜€ ชปํ•จ„ ธ‹ํ•ด• ํ•œ‹ค.

6.2. ํ•ญชฉ 36. ธํ„ฐํŽ˜ดŠค „Š ตฌํ˜„ „Š˜ ฐจด „ ดํ•ดํ•˜.

{{|
class Shape
{
...

public:
virtual void draw() const;
}
class Rectangle : public Shape { ... };
class Ellipse : public Shape { ... };

...

Shape *ps1 = new Rectangle;
ps1->draw();
Shape *ps2 = new Ellipse;
ps2->draw();
|}}
ํดž˜Šค Shape—„œŠ” ตฌํ˜„ํ•  ‚ดšฉ˜ „„งŒ žˆ‹ค.
ทธฆฌณ  ƒ†ฐ›€ ํดž˜Šค“ค—„œ ‚ดšฉ˜ ตฌํ˜„ด žˆ‹ค.

งŒ•ฝ ƒ†ฐ›€ ํดž˜Šค—„œ €ƒํ•จˆ˜˜ ตฌํ˜„ด ˜–ด žˆ€ •Š„ ฒฝšฐ€ žˆ‹ค.
ดŸด•Œ €ƒํ•จˆ˜กœ „ •œ ํ•จˆ˜ ‹คํ–‰ํ•œ‹คฉด ฌธ œ€ œ‹ค.
{{|
class Shape
{
...

public:
virtual void draw const = 0;

protected:
void defaultdraw() const;
}

class Rectangle : public Shape
{
...

public:
virtual void draw() const
{
defaultdraw();
}
}
|}}
ด ‡ฒŒ €ƒํ•จˆ˜ ˆœˆ˜€ƒํ•จˆ˜กœ ฐ”พธณ  ทธ— ”ฐฅธ ธฐณธํ–‰™— Œ€ํ•œ  •˜ defaultํ•จˆ˜กœ ํ•˜‚˜ งŒ“ค–ด ‘Š”ฒƒ„ ข‹€ ฐฉฒ•ด‹ค.

6.3. ํ•ญชฉ 37. „Šœ „€ƒ ํ•จˆ˜ žฌ •˜ํ•˜€ •Š„ก ํ•œ‹ค.

€ƒํ•จˆ˜™€ „€ƒํ•จˆ˜˜ ‚ฌšฉฒ•— Œ€ํ•œ ‚ดšฉด‹ค.
ƒ†ด ˜Š” ํ•จˆ˜— Œ€ํ•˜—ฌ €ƒํ•จˆ˜กœ „ •ํ•˜Š”ฒŒ ˜ณณ  ƒ†ด ˜€ •Š‚˜ ƒ†ด ˜”„ ‹ค‹œ ตฌํ˜„ด ˜€ •Š‹คฉด „€ƒํ•จˆ˜กœ ‚ฌšฉ˜–ด• ํ•œ‹ค.

6.4. ํ•ญชฉ 38. „Šœ €žฌ ธžฐ’„ žฌ •˜ํ•˜€ •Š„ก ํ•œ‹ค.

{{|
enum ShapeColor { RED, GREEN, BLUE };

class Shape
{
...

public:
virtual void draw(ShapeColor = RED) const;
}
class Rectangle : public Shape
{
...
public:
virtual void draw(ShapeColor = BLUE) const;
};

...

Shape *pr = new Rectangle;
pr->draw();
|}}
ด™€ ฐ™€ ฒฝšฐ prด ํŒŒž€ƒ‰ ‚ฌฐํ˜•„ ทธฆดฒƒด ˜ˆƒ€ ํ•˜€งŒ ทธ ‡€ •Š‹ค.
pr€ Shapeํ˜•˜  •  ํฌธํ„กœ ””ํดํŠธธž™€Š”  • œกœ ฒฐํ•ฉํ•œ‹ค.
ฒฐตญ „ƒ‰ ‚ฌฐํ˜•ด ทธ ค„‹ค.

ดŠ” „Šฅƒ˜ ดœ ธฐ ””ํดํŠธธž™€ ™ œกœ ฒฐํ•ฉ‹œ ณตžกํ•˜ณ  ŠฆฌฒŒ ž‘™ํ•œ‹ค.
Œ€‹  กฐธˆ ”  ฅดฒŒ ‹คํ–‰ด œ‹ค.

6.5. ํ•ญชฉ 39. „ธต„˜ •„ž˜ชฝ ํดž˜Šค ‹คšดบŠคํŠธ(downcast)ํ•˜€ •Š„ก ํ•œ‹ค.

{{|
class Person { ... };
class Student : public Person { ... };

...

Student *s = new Person;
|}}
ดฒƒ€ ˜ณ€ •Š‹ค. ญ 100›งœฆฌ ™ „งŒ “ค–ดฐˆ ˆ˜ žˆŠ”  €ธˆํ†ต— 500›งœฆฌ ™ „„ šฐฒจ „Š”ฒƒ ฐ™‹ค.
ทธŸฌ€กœ s ํ†ตํ•ด StudentงŒ˜ ํ•จˆ˜ ํ˜ธถœ‹œ •Œˆ˜ —†Š” ฒฐ ‚˜ํƒ€‚ ฒƒด‹ค.

˜„กดฉด ดŸฐ ฒฝšฐŠ” €ƒํ•จˆ˜™€ ํดž˜Šค˜ „ธตตฌกฐ ํ†ตํ•œ ธํ„ฐํŽ˜ดŠค˜ ํ™œšฉœกœ ํ•ดฒฐํ•œ‹ค.
ํ•˜€งŒ ด ‡ฒŒ ํ’€ฆฌ€ •Š„ ฒฝšฐ dynamic_cast™€ ฐ™€ ฐฉฒ•œกœ ฆฌ ํƒ€ž…„ ฒดํฌํ•œํ›„ ‹คํ–‰—ฌ€ ฒฐ •ํ•˜„ก ํ•˜ž.

6.6. ํ•ญชฉ 40.  ˆด–ดง(layering)„ ํ†ตํ•ด "€€ณ  žˆŠ”" ฒƒ "‚ฌšฉํ•˜—ฌ ตฌํ˜„œ" ฒƒ„ ชจธงํ•˜„ก ํ•˜ž.

Compositionœกœ„ ถˆฆฌŠ” "has-a" €„˜ ด•ธฐ ด‹ค.

งŒ•ฝ STL˜ ํฌํ•จœ setด™ธ— ž‹ งŒ˜ Set„ ตฌํ˜„ํ•˜ณ ž ํ•˜Š” ˜ˆ œ€ žˆ‹ค.
{{|
template<class T> class Set: public list<T> { ... };
|}}
ดฒƒ€ ˜ณ‹คณ  ณดด‚˜ ทธ ‡€ •Š‹ค.
™œƒํ•˜ฉด Derived€ Baseดฉด (isa), Base€ ฐธ•Œ ํ•ญƒ Derived„ ฐธด œ‹ค.
Set€ ค‘ณตœ ‚ดšฉ— Œ€ํ•ด„œ ํ•œฒˆงŒ ž… ฅ„ ฐ›Š” žฃŒํ˜•ด‹ค. ํ•˜€งŒ ด ‡ฒŒ "isa" €„กœ ‚˜ํƒ€‚•Œ ˜ณ€ ชปํ•˜ฒŒ œ‹ค.

{{|
template<class T> class Set
{
...

public:
void insert(const T &ํ•ญชฉ);
private:
list<T> rep;
}

...

template<class T> void Set<T>::insert(const T& ํ•ญชฉ);
{
// ค‘ณตœ ‚ดšฉด žˆŠ”€ €‚ฌํ›„ ถ”€
}
|}}
ด ‡ฒŒ ตฌํ˜„ํ•œ‹คฉด ํ•ดฒฐด œ‹ค.

"isa" €„™€ "has-a"€„ค‘ –ดŠฒƒธ€ ƒฐํ•˜ณ  ตฌํ˜„ํ•˜ž.

6.7. ํ•ญชฉ 41. „Š ํ…œํ”Œฆฟ˜ ฐจด „ ดํ•ดํ•œ‹ค.

ํ…œํ”Œฆฟ€ ฐฒด˜ ํƒ€ž…ด ํดž˜Šค˜  •˜œ ํ•จˆ˜“ค˜ ™ž‘ ›ฆฌ— ˜ํ–ฅ„ ˜€ •ŠŠ” ฒฝšฐ—, ํดž˜Šค˜ ชจŒ„ ƒ„ํ•˜Š” ฐ ‚ฌšฉ˜–ด• ํ•œ‹ค.
„Š€ ฐฒด˜ ํƒ€ž…ด ํดž˜Šค—  •˜œ ํ•จˆ˜“ค˜ ™ž‘ ›ฆฌ— ˜ํ–ฅ„ ˜Š” ฒฝšฐ—, ํดž˜Šค˜ ชจŒ„ œ„ํ•ด ‚ฌšฉ˜–ด• ํ•œ‹ค.

งŒ•ฝ Šคํƒ„ ํ…œํ”Œฆฟด •„‹Œ „Š„ ํ†ตํ•ด ตฌํ˜„ํ•˜ณ ž ํ•œ‹คฉด –ด–ปฒŒ ํ• ฒƒธ€ ƒฐํ•ด ณดณ 
ƒ->™->ธ„->ํ•™ƒ“˜ ํ˜•‹„ ํ…œํ”Œฆฟœกœ ตฌํ˜„ํ•˜ณ ž ํ•œ‹คณ  ƒฐํ•ดณดž.

ํ…œํ”Œฆฟด •„‹Œ „Š„ ํ†ตํ•œ Šคํƒ˜ ตฌํ˜„ดฉด voidํ˜• ํฌธํ„“„ ํ†ตํ•ด —ฌŸฌ žฃŒํ˜•„ ™ œกœ ž… ฅฐ›„ก …ธ ฅํ•  ฒƒดฉฐ
„ธตตฌกฐ ํ…œํ”Œฆฟœกœ ฌถณ ž ํ•œ‹คฉด ํ…œํ”Œฆฟํ˜•— ”ฐ ifฌธ„ ŒฆฌŠ”“ C, PASCAL˜ ํ˜•‹„ ”ฐ€„ ชจฅธ‹ค.

6.8. ํ•ญชฉ 42. private „Š„ ฐ”ฅดฒŒ ‚ฌšฉํ•˜.

private „Š€ layering งคšฐ œ ‚ฌํ•˜‹ค. public „ŠŠ” ‹คฅดฒŒ Derived isa Baseด€„ •Š‹ค.
‹จ€ layering ฐจด € Baseํดž˜Šค—„œ protected private˜ ‚ฌšฉœ ฌด˜ ฐจดด‹ค.
งŒ•ฝ งŒ“คณ ž ํ•˜Š” ํดž˜Šค€ ‹คฅธ ํดž˜Šค˜ protected‚˜ privateฉค„ ‚ฌšฉํ•ด• ํ•œ‹คฉด layeringงŒœกœŠ” ฒ˜ฆฌํ• ˆ˜€ —†‹ค.
ดŸด•Œ private „Š„ ‚ฌšฉํ•ด•ํ•œ‹ค.

{{|
class GenericStack
{
...

public:
void push(const void *Object);
void *pop();
}
|}}
ด ‡ฒŒ ฐฒด€ •„‹Œ ํฌธํ„— Œ€ํ•œ Šคํƒด žˆ‹คณ  ํ• •Œ. ด ํดž˜ŠคงŒœกœŠ” ํƒ€ž…ด •ˆ •ํ•˜€ ชปํ•˜‹ค.

{{|
class GenericStack
{
protected:
... // ƒ„ž, †Œฉธž ฐ ƒžตœ ‚ดšฉ

void push(const void *Object);
void *pop();
}

class IntStack : private GenericStack
{
...

public:
void push(int *intPtr)
{
GenericStack::push(intPtr);
}
int *pop()
{
return static_cast<int*>(GenericStack::pop());
}
}

...

GenericStack gs; // —Ÿฌ : ƒ„ž€ protectedด‹ค.
IntStack is; // Int ํฌธํ„ฐํ˜•— Œ€ํ•œ •ˆ •ํ•œ Šคํƒด‹ค.
|}}
ํƒ€ž…•ˆ •ํ•˜ณ  GenericStackงŒœกœŠ” ƒ„ํ•  ˆ˜ —†„ก ง‰•„†“•˜‹ค.

Œ€€„˜ ฒฝšฐ layeringด “ฐณ  ด™€ ฐ™ด ํŠ„ํ•œ ฒฝšฐงŒ private „Š„ “ฐ„ก ํ•˜ž.

6.9. ํ•ญชฉ 43. ‹คค‘ „Š„ ฐ”ฅดฒŒ ‚ฌšฉํ•˜„ก ํ•˜.

‹คค‘ „Š€ • งคชจํ˜ธํ•œ €„ด งŽ‹ค.

{{|
class A { ... };
class B : public A { ... };
class C : public A { ... };
class D : public B, public C { ... };
|}}
ด™€ ฐ™€ ฒฝšฐ งคšฐ ค‘ณต ดณ  งคšฐ œ„ํ—˜ํ•œ ฝ”“œด‹ค.
ํดž˜Šค A€„— žˆŠ” €ƒํ•จˆ˜ B™€ C—„œ ตฌํ˜„ํ•˜˜€‹คฉด ํดž˜Šค D—„œ ํ˜ธถœ˜Š” €ƒํ•จˆ˜Š” ฌด—‡„ œปํ•˜Š”€ •Œˆ˜ —†‹ค.
ดฒƒ€ ตœ•…˜ „„กœ ดŸฐ ฐฉฒ•€ ํ”ํ•ด• ํ•œ‹ค.

ตœŒ€ํ•œ œ„™€ ฐ™€ ‹คด•„ชฌ“œํ˜• ƒ†€ ํ”ํ•˜ž.
žฐ”—„œŠ” ƒ†ฐ›„ ํดž˜ŠคŠ” ํ•˜‚˜งŒ ฐ›„ˆ˜ žˆณ  ธํ„ฐํŽ˜ดŠคŠ” —ฌŸฌ€€ ฐ›„ ˆ˜ žˆ‹ค.

6.10. ํ•ญชฉ 44. ˜ธํ•˜Š” ฐ” ํ‘œํ˜„ํ•˜„ก ํ•˜. ž‹ ด ํ‘œํ˜„ํ•œ ฒƒ˜ ˜ ดํ•ดํ•˜„ก ํ•˜.

œ„˜ ‚ดšฉ„ š”•ฝํ•œ ‚ดšฉด‹ค.

7. ฌ˜ํ•œ €„

7.1. ํ•ญชฉ 45. C++€ €€ํ•˜ฒŒ –ด–ค ํ•จˆ˜ งŒ“ค–ดณ  ํ˜ธถœํ•˜Š”€ ดํ•ดํ•˜ธฐ

{{|
class Empty { };
|}}
งŒ•ฝ ด ‡ฒŒ ํดž˜Šค ƒ„ํ•œ‹คฉด

{{|
class Empty
{
public:
Empty();
Empty(const Empty& rhs);
~Empty();

Empty& operator=(const Empty& rhs);
Empty* operator();
const Empty* operator&() const;
}
|}}
ด ‡ฒŒ งŒ“ค–ด€‹ค.

7.2. ํ•ญชฉ 46. ‹คํ–‰ ‹œ„ —Ÿฌณด‹คŠ” ปดํŒŒ ‹œ„ งํฌ ‹œ„ —Ÿฌ€ ข‹‹ค.

C++€ ปดํŒŒ˜Š” –ธ–ดกœ ‹คํ–‰‹œ„—Š” —Ÿฌ ํƒ€ํ•˜€ •ŠŠ”‹ค.
ทธ Œ€‹   ฅธ ˆ˜ํ–‰‹œ„˜ ดตด žˆณ  ‹คํ–‰ ‹œ„˜ —Ÿฌ ˜ˆฐฉํ•˜ธฐ œ„ํ•ด„œ ปดํŒŒ ‹œ„ งํฌ ‹œ„— œ„ํ—˜„  œฐํ•˜„ก ํ•ด• œ‹ค.

‚ งœ ‚˜ํƒ€‚ดธฐ œ„ํ•œ ํดž˜Šค ด‹ค.
{{|
class Date
{
...

public:

Date(int day, int month, int year);
}
|}}
—ฌธฐ„œ Month˜ ฐ’˜ œ ํšจ„ ฒดํฌ œ„ํ•ด„œ ณ ณณดž.
{{|
class Date
{
...

public:

Date(int day, const Month& month, int year);
}

class Month
{
public:
static const Month Jan() { return 1; };
static const Month Feb() { return 2; };
...
static const Month Dec() { return 12; };
private:
Month(int number) : monthNumber(number) { }
Month(const Month& rhs);
const int monthNumber;
};

...

Date d(30,Month::Sep(),2003);
|}}
ด™€ ฐ™€ ฐฉฒ•œกœ MonthŠ” ‹คํ–‰‹œ„— €‚ฌ ํ•ด• ํ•  ‚ดšฉ„ ปดํŒŒ ‹œ„œกœ ˜ฎธธˆ˜ žˆ‹ค.

7.3. ํ•ญชฉ 47. „€—ญ  • (Non-local static) ฐฒดŠ” ‚ฌšฉ˜ธฐ  „— ดˆธฐํ™”˜„ก ํ•ด• ํ•œ‹ค.

งŒ•ฝ ํŒŒ‹œŠคํ…œด ดˆธฐํ™”œํ›„ ”” ‰ํ† ฆฌ ‹œŠคํ…œ˜ €„œกœ ดˆธฐํ™” ˜–ด• ํ•œ‹คฉด
ฐ˜“œ‹œ ทธ ‡ฒŒ ํ•˜„ก ํ•ด•ํ•œ‹ค.

ทธŸฌ‚˜ „€—ญ ฐฒดกœ „ –ธด ˜–ด žˆ‹คฉด ดˆธฐํ™” ˆœ„œ  •ํ•˜ธฐ€ งคšฐ ํž˜“ค ฒƒด‹ค.
(„€—ญ ฐฒดŠ”  „—ญด‚˜ „ž„ŠคํŽ˜ดŠค ˜—ญด‚˜ ํดž˜Šค‚ด static, ํŒŒ ˜—ญ˜ static—  •˜œ ฒฝšฐด‹ค.)

ดŸด •ŒŠ”
{{|
FileSystem& theFileSystem()
{
static FileSystem tfs;
return tfs;
}

...

class Directory
{
...
public:
Directory()
{
// theFileSystem ํ•จˆ˜ ํ˜ธถœํ•˜—ฌ ”” ‰ํ† ฆฌ €„„ ดˆธฐํ™” ‹œํ‚จ‹ค.
}
}
|}}
ด ‡ฒŒ ํ•จœกœ ฐ˜“œ‹œ Directoryํดž˜Šค€ ดˆธฐํ™” ˜ธฐ „— FileSystem„ ดˆธฐํ™” ‹œํ‚ฌˆ˜ žˆ‹ค.

7.4. ํ•ญชฉ 48. ปดํŒŒŸฌ˜ ฒฝณ (Warning)— ˜ ธฐšธ—ฌ.

C++ –ธ–ดŠ” œ —ฐํ•˜‹ค.
{{|
class B
{
public:
virtual void f() const;
}

class D
{
public:
virtual void f();
}
|}}
ด™€ ฐ™ด žฌ •˜ ํ•˜˜€„ •Œ, Error€ •„‹Œ Warning„ งŒ“ค–ด ‚ˆ˜„ žˆ‹ค.

ErrorฟงŒ •„‹ˆ Warning—„ ˜ ธฐšธดž. ž žฌ ธ ฌธ œ š”†Œ€  ˆ˜„ žˆ‹ค.

7.5. ํ•ญชฉ 49. ํ‘œ€ ดธŒŸฌฆฌ ž˜ •Œ•„‘ž.

ํ‘œ€ ดธŒŸฌฆฌŠ” œ šฉํ•˜‹ค!

7.6. ํ•ญชฉ 50. C++— Œ€ํ•œ ดํ•ด „“ํ˜€.

ทธƒฅ ฝ–ด ฒƒ.


8. Thread

ทธƒฅ ณดฉด ˆ ˆ ˆ  „˜–ด €Š”ฐ.. “ฐ ค‹ˆ ง‰ง‰ํ•˜ตฌ‚˜.. guts__

Effective C++ ‚ดšฉ„ ณดฉด„œ ดธ ํ•ญชฉ 21 Œ€Š”  •ฆฌ€ ˜–ด žˆ”ตฐš”.
ทธž˜„œ ทธ ดํ•˜ ‚ดšฉ„  •ฆฌํ•ด ˜ฌฆฌณ  ‹ถŠต‹ˆ‹ค. -- ‹คฅธํ•™ตปดํ“จํ„ณตํ•™€
ดณณ—Š” ํŠ„ํžˆ ํ—ˆฝ„ ํ•˜‚˜, ํ—ˆฝ„ ฐ›„งŒํ•œ ‚ฌžŒด —†Šต‹ˆ‹ค. –ธ œ“  ํ™˜˜ž…‹ˆ‹ค :) --sun

•ˆํ˜€ํ˜•ด ฝœณ  ถ”ฒœํ•ด € ….. € œ„ํ‚ค— ฉ‹€ฒŒ„  •ฆฌ€ ˜–ดžˆตฐš”.  „ ……„ ‚˜€€ ชปํ•˜‹ˆ ํ˜ž„œ„ —ด‹ฌํžˆ ํ•ด•ฒ Šต‹ˆ‹ค. - ถŒ˜ธฐ

Valid XHTML 1.0! Valid CSS! powered by MoniWiki
last modified 2021-02-07 05:23:10
Processing time 0.3119 sec