Sophie

Sophie

distrib > Mandriva > 2010.0 > i586 > media > contrib-release > by-pkgid > d40f11cf5b21d4287bbb5af7cbeec0a9 > files > 11

howto-text-ko-2006-5mdv2010.0.noarch.rpm

  C++ Programming HOW-TO

  Al Dev (Alavoor Vasudevan)        alavoor@yahoo.com
  v5.0, 4¿ù 9ÀÏ  2000
  ±è ÁöÈñ, À± ÁÖö
  2000³â 6¿ù 15ÀÏ

  ÀÌ ¹®¼­´Â C++ÀÇ ¸Þ¸ð¸® ¹®Á¦¸¦ ÇÇÇÏ´Â ¹æ¹ý¿¡ ´ëÇØ ´Ù·ç¸ç C++¾ð¾î¸¦
  ¿Ã¹Ù¸£°Ô ÇÁ·Î±×·¥ ÇÒ¼ö ÀÖµµ·Ï µµ¿Í ÁÖ°íÀÚ ÇÑ´Ù.  ÀÌ ¹®¼­ÀÇ Á¤º¸´Â ¸ðµç
  ¿î¿µÃ¼Á¦ - ¸®´ª½º, MS DOS, ¾ÖÇà ¸ÆŲÅä½Ã, À©µµ¿ì 95/NT, OS/2, IBM
  ¿î¿µÃ¼Á¦µé, VMS, Novell Netware, À¯´Ð½ºÀÇ ¸ðµç Á¾·ù (¼Ö¶ó¸®½º, HPUX,
  AIX, SCO, Sinix, BSCµî..), ±×¸®°í "C++" ÄÄÆÄÀÏ·¯¸¦ Áö¿øÇÏ´Â ¸ðµç ´Ù¸¥
  ¿î¿µÃ¼Á¦µé (´Ù½Ã ¸»ÇØ ÀÌ Áö±¸»ó¿¡ Á¸ÀçÇÏ´Â °ÅÀÇ ¸ðµç ¿î¿µÃ¼Á¦µéÀ̶ó°í
  ÇÒ ¼ö ÀÖ´Ù)- ¿¡ Àû¿ëµÉ¼ö ÀÖ´Ù.
  ______________________________________________________________________

  ¸ñÂ÷

  1. ¼­·Ð
     1.1 ÇöÀç C++ ÄÄÆÄÀÏ·¯µéÀÌ Á÷¸éÇÑ ¹®Á¦µé
     1.2 "C" ¸¦ ¾µ°ÍÀΰ¡ "C++" À» ¾µ°ÍÀΰ¡ ¾Æ´Ï¸é ÀÚ¹Ù¸¦ ¾µ°ÍÀΰ¡?

  2. ´Ù¿î·Îµå mychar AID CDATA Download mychar(LABEL)LABEL
  3. mychar classÀÇ »ç¿ë
     3.1 ¿¬»êÀÚµé
     3.2 ÇÔ¼öµé
     3.3 ±âŸ ÇÔ¼öµé

  4. C++ Zap (Delete) ¸í·É¾î AID CDATA zap(LABEL)LABEL
  5. my_malloc °ú my_freeÀÇ »ç¿ë AID CDATA my_malloc(LABEL)LABEL
  6. Debug È­Àϵé
  7. C++ Online ¹®¼­µé
     7.1 C++ Æ©Å͸®¾óµé
     7.2 C++ ÄÚµù Ç¥ÁØ
     7.3 C++ Äü ·¹ÆÛ·±½º
     7.4 C++ À¯Áî³Ý ´º½º±×·ìµé

  8. ¸Þ¸ð¸® µµ±¸µé
  9. °ü·Ã URLµé
  10. ÀÌ ¹®¼­ÀÇ ´Ù¸¥ Æ÷¸äµé
  11. ÀúÀÛ±Ç
  12. ÷ºÎ A example_mychar.cpp  AID CDATA Appendix A(LABEL)LABEL
  13. ÷ºÎ B mychar.h  AID CDATA Appendix B(LABEL)LABEL
  14. ÷ºÎ C mychar.cpp AID CDATA Appendix C(LABEL)LABEL
  15. ÷ºÎ D my_malloc.cpp  AID CDATA Appendix D(LABEL)LABEL
  16. ÷ºÎ E my_malloc.h  AID CDATA Appendix E(LABEL)LABEL
  17. ÷ºÎ F debug.h AID CDATA Appendix F(LABEL)LABEL
  18. ÷ºÎ G debug.cpp AID CDATA Appendix G(LABEL)LABEL
  19. ÷ºÎ H Makefile AID CDATA Appendix H(LABEL)LABEL

  ______________________________________________________________________

  1.  ¼­·Ð

  C++ Àº °¡Àå ³Î¸® ¾²ÀÌ´Â ¾ð¾îÀÌ°í, ¾ÕÀ¸·Ð ÀÚ¹ÙÀÇ µîÀå°ú´Â »ó°ü¾øÀÌ ¿À·£
  ±â°£µ¿¾È ¾²ÀÏ °ÍÀÌ´Ù.  C++ Àº ¸Å¿ì ºü¸£°Ô ½ÇÁ¦·Î ÀÚ¹Ùº¸´Ù 20³»Áö 30¹è
  ´õ »¡¸® ½ÇÇàµÈ´Ù. ÀÚ¹Ù´Â "virtual engine"À§¿¡¼­ ÀÛµ¿µÇ´Â ¹ø¿ª
  (interpreted)¾îÀ̱⶧¹®¿¡ ¸Å¿ì ´À¸®°Ô ½ÇÇàµÈ´Ù. ÀÚ¹Ù¿¡¼­ ¸Þ¸ð¸® °ü¸®´Â
  ÀÚµ¿ÀÌ¶ó¼­ ÇÁ·Î±×·¡¸ÓµéÀº ¸Þ¸ð¸® ¾ó·ÎÄÉÀÌ¼Ç (allocation) À» Á÷Á¢
  ´Ù·çÁö ¾Ê´Â´Ù. ÀÌ ¹®¼­´Â C++ »ç¿ëÀ» ´õ¿í ÆíÇÏ°Ô Çϱâ À§ÇØ C++ ¿¡¼­ÀÇ
  ¸Þ¸ð¸® °ü¸®¸¦ ÀÚµ¿È­ÇÏ´Â °ÍÀ» ½ÃµµÇÑ´Ù. ÀÚ¹ÙÀÇ ÁÁÀº Á¡ ¸Þ¸ð¸®
  ¾ó·ÎÄÉÀ̼ÇÀÌ ÀÚµ¿ÀûÀ¸·Î 󸮵ȴٴ °ÍÀÌ´Ù. ÀÌ howto´Â "C++"ÀÌ ¸Þ¸ð¸®
  °ü¸®¸é¿¡¼­ ÀÚ¹Ù ¾ð¾î¿Í(¸¦) "°æÀï/¸ð¹æ"ÇÏ´Â °ÍÀ» °¡´ÉÇÏ°Ô ÇÒ °ÍÀÌ´Ù.

  C++ ÇÁ·Î±×·¡¸ÓµéÀº ¼öµ¿ ¸Þ¸ð¸® ¾ó·ÎÄÉÀ̼Ƕ§¹®¿¡ ¸¹Àº ½Ã°£À» ¼ÒºñÇÑ´Ù.
  ÀÌ ¹®¼­¿¡ ÀÖ´Â Á¤º¸´Â ¿©·¯ºÐ¿¡°Ô µð¹ö±ëÇÏ´Â ½Ã°£À» ÁÙÀÏ ¼ö ÀÖ´Â ´õ
  ³ªÀº ¾ÆÀ̵ð¾î¿Í ÆÁµéÀ» Á¦°øÇÒ °ÍÀÌ´Ù.

  1.1.  ÇöÀç C++ ÄÄÆÄÀÏ·¯µéÀÌ Á÷¸éÇÑ ¹®Á¦µé

  C++ Àº CÀÇ super-set ÀÎ °ü°è·Î "C" ¾ð¾îÀÇ ¸ðµç ¾ÈÁÁÀº Á¡µéÀ» °®°í
  ÀÖ´Ù.  ¿¹¸¦ µé¾î, "C" ÇÁ·Î±×·¡¹Ö¿¡¼­´Â ¸Þ¸ð¸® À¯Ãâ°ú ¸Þ¸ð¸®
  ¿À¹öÇ÷ο찡 ÈçÇÏ´Ù.  ¿Ö³Ä¸é ´ÙÀ½°ú °°Àº ¿ë·Ê¶§¹®¿¡

  ______________________________________________________________________
          Datatype  char * and char[]
          String functions like strcpy, strcat, strncpy, strncat, etc..
          Memory functions like malloc, realloc, strdup, etc..
  ______________________________________________________________________

  char * ¿Í strcpyÀÇ »ç¿ëÀº "overflow" "fence past errors", ±×¸®°í "mem­
  ory leaks" ·Î ÀÎÇÑ Áöµ¶ÇÑ ¸Þ¸ð¸® ¹®Á¦µéÀ» ¾ß±â½ÃŲ´Ù.  ¸Þ¸ð¸® ¹®Á¦µéÀº
  µð¹ö±×ÇÏ±â ¸Å¿ì ¾î·Æ°í, °íÄ¡°í trouble-shootÇϴµ¥ ¸¹Àº ½Ã°£À»
  ¼Ò¸ð½ÃŲ´Ù.  ¸Þ¸ð¸® ¹®Á¦µéÀº ÇÁ·Î±×·¡¸ÓµéÀÇ »ý»ê¼ºÀ» °¨¼Ò½ÃŲ´Ù. ÀÌ
  ¹®¼­´Â "C++"ÀÇ ¸Þ¸ð¸® ¹®Á¦¸¦ ÇؼÒÇÒ ¼ö ÀÖ´Â  ¿©·¯°¡Áö ¾ð±ÞµÈ ¹æ¹ýµéÀ»
  ÅëÇØ ÇÁ·Î±×·¡¸ÓµéÀÇ »ý»ê¼ºÀ» Áõ  ½ÃÅ°´Â°ÍÀ» µ½´Â´Ù. ¸Þ¸ð¸®¿Í °ü·ÃµÈ
  ¹ö±×µéÀº Å©·¢ÇÏ±â ¸Å¿ì ¾î·Æ°í ½ÉÁö¾î ¼÷·ÃµÈ ÇÁ·Î±×·¡¸Óµéµµ ¸Þ¸ð¸®¿Í
  °ü·ÃµÈ ¹®Á¦Á¡µéÀ» µð¹ö±×Çϴµ¥ ¸îÀÏ, ¸îÁÖ È¤Àº ¸î´Þ±îÁö °É¸®±âµµ ÇÑ´Ù.
  ¿©·¯°³ÀÇ ¸Þ¸ð¸® ¹ö±×µéÀº  ¸î°³¿ùµ¿¾È ÄÚµå¾È¿¡ "¼û¾î"ÀÖÀ» °ÍÀÌ°í
  ±×°ÍµéÀº ±â´ëÄ¡ ¾Ê¾Ò´ø ÇÁ·Î±×·¥ Ãæµ¹À» ¾ß±â½Ãų ¼ö ÀÖ´Ù. char * ÀÇ
  »ç¿ëÀº  ¹Ì±¹°ú ÀϺ»¿¡¼­ µð¹ö±ë ÇÏ´Â ½Ã°£°ú ÇÁ·Î±×·¥ÀÇ ½ÇÇàÁ¤Áö·Î ¸Å³â
  20¾ïºÒÀÇ ¼ÕÇظ¦ ¾ß±â½ÃÅ°°í ÀÖ´Ù. ¿©·¯ºÐÀÌ C++ ¿¡¼­ char * ¸¦ »ç¿ëÇϸé,
  ƯÈ÷ ¿©·¯ºÐÀÇ ÇÁ·Î±×·¥ÀÌ ¹é¸¸ÁÙ ÀÌ»óÀÇ Äڵ尡 ÀÖ´Ù¸é ±×°ÍÀº Á¤¸»·Î
  ¼ÕÇغ¸´Â ÀÏÀÌ´Ù,

  ±×·¡¼­ ´ÙÀ½ÀÇ ±â¼úµéÀÌ "C" ¾ð¾îÀÇ ¾àÁ¡À» ±Øº¹Çϱâ À§ÇØ ´ÙÀ½ÀÇ ±â¼úµéÀ»
  Á¦¾ÈÇÏ´Â °ÍÀÌ´Ù.

  C++ ÄÄÆÄÀÏ·¯µéÀº ÇÁ·Î±×·¡¸ÓµéÀÌ "char *" , "char[]" µ¥ÀÌÅÍ Å¸ÀÔ°ú
  strcpy, strcat, strncpy, strncat°ú °°Àº ÇÔ¼öµéÀ» »ç¿ëÇÏ´Â °ÍÀ»
  ¸·¾Æ¾ßÇÑ´Ù°í Á¦¾ÈÇÑ´Ù. char *, char[] ¿Í °°Àº µ¥ÀÌÅÍŸÀÔµé°ú strcpy,
  strcat °°Àº ÇÔ¼öµéÀº C++ÀÇ »ç¿ë¿¡ À־ ¹Ýµå½Ã ¿ÏÀüÈ÷ ±ÝÁöµÇ¾î¾ß¸¸
  ÇÏ´Â ÇØ·Î¿î °ÍµéÀÌ´Ù!!

  ¸ðµç C++ ÇÁ·Î±×·¡¸ÓµéÀº char * and char[] ¸¦ »ç¿ëÇÏ´Â ´ë½Å¿¡ ÀÌ ¹®¼­¿¡
  ³ª¿À´Â 'mychar class'¿Í STDLIB¿¡ Æ÷ÇÔµÈ 'string class' ¸¦ ¹Ýµå½Ã
  »ç¿ëÇØ¾ß ÇÑ´Ù. 'mychar class' ´Â »ý¼ºÀÚ¿Í ¼Ò¸êÀÚ¸¦ ÀÌ¿ëÇؼ­ ¸Þ¸ð¸®
  °ü¸®¸¦ ÀÚµ¿È­ÇÏ°í ltrim, substringµîµîÀÇ ¿©·¯ ÇÔ¼öµéÀ» Á¦°øÇÑ´Ù.

  C++ ÄÄÆÄÀÏ·¯¿¡ ÀÖ´Â 'string class' µµ ¶ÇÇÑ º¸ÀÚ. string class ´Â
  standard GNU C++ library ÀÇ ÀϺκÐÀÌ°í ¸¹Àº stringÁ¶ÀÛÇÔ¼ö   Á¦°øÇÑ´Ù.
  string class' ¿Í 'mychar class' ¸¦ ¾²¸é char * datatypeÀ» ¾µ ÇÊ¿ä°¡
  ¾ø¾îÁø´Ù.  ¶ÇÇÑ, C++ ÇÁ·Î±×·¡¸ÓµéÀº 'malloc' À̳ª 'free'¸¦ ¾²´Â ´ë½Å
  'new'¿Í class' ´Â ¿Ïº®ÇÏ°Ô char datatypeÀ» ´ë½ÅÇØ ¾²ÀÏ ¼ö ÀÖ´Ù. ´õ±¸³ª
  ÇÁ·Î±×·¡¸ÓµéÀº ¸Þ¸ð¸® ¹®Á¦¿Í ¸Þ¸ð¸® ¾ó·ÎÄÉÀ̼ǿ¡ ´ëÇؼ­ ÀüÇô °ÆÁ¤ÇÒ
  ÇÊ¿ä°¡ ¾øÀ¸´Ï ¾ó¸¶³ª ÀÌ·Î¿î °ÍÀΰ¡.

  GNU C++ ÄÄÆÄÀÏ·¯´Â char *, char[] datatypes ÀÇ Áö¿øÀ» ¹Ýµå½Ã
  ÁßÁöÇؾßÇϸç, char datatypeÀ» ÀÌ¿ëÇÑ ±¸ÇÁ·Î±×·¥À» ÄÄÆÄÀÏÇ챉   Çؼ­
  ÄÄÆÄÀÏ·¯´Â "-fchar-datatype" ¶ó ºÒ¸®´Â ¿É¼ÇÀ» g++ ¸í·É¾î¿¡ ´õ Ãß°¡·Î
  Á¦°øÇØÁà¾ß ÇÑ´Ù.  ¾ÕÀ¸·Î 2³â¾È¿¡ ¸ðµç C++ ÇÁ·Î±×·¥µéÀº 'mychar class'
  and 'string class' ¸¦ ¾²°Ô µÉ°ÍÀÌ°í char * and char[] ´Â »ç¶óÁö°Ô µÉ
  °ÍÀÌ´Ù. ÄÄÆÄÀÏ·¯´Â ¾ÈÁÁÀº ÇÁ·Î±×·¡   ½À°üÀ» ¹æÁöÇϵµ·Ï ³ë·ÂÇؾßÇÑ´Ù.

  1.2.  "C" ¸¦ ¾µ°ÍÀΰ¡ "C++" À» ¾µ°ÍÀΰ¡ ¾Æ´Ï¸é ÀÚ¹Ù¸¦ ¾µ°ÍÀΰ¡?

  ¸ðµç ÀÀ¿ëÇÁ·Î±×·¥À̳ª ÀÏ¹Ý ¸ñÀûÀÇ ÇÁ·Î±×·¡¹ÖÀ» À§Çؼ­´Â °´Ã¼ÁöÇâÀûÀÎ
  ¾ð¾îÀÎ "C++"À» ÀÌ¿ëÇؼ­ ÇÁ·Î±×·¡¹ÖÀ» Çϴ°ÍÀÌ ÃßõµÈ´Ù. "C++"ÀÇ
  °´Ã¼ÁöÇâ ±â´ÉÀ» ÃæºÐÈ÷ À¯¿ëÇÒ ¼ö ÀÖ´Ù. ÇÏÁö¸¸ -0À̳ª -03°ú °°Àº
  ÄÄÆÄÀÏ·¯ optimizer¿É¼ÇµéÀº C++ÀÇ ¼Óµµ¸¦ Áõ°¡½Ãų ¼ö ÀÖ´Ù.

  ¿äÁò¿£ "C" ¾ð¾î°¡ ¿î¿µÃ¼Á¦, µð¹ÙÀ̽º µå¶óÀ̹öµîÀ» °³¹ßÇϱâÀ§ÇÑ "½Ã½ºÅÛ
  ÇÁ·Î±×·¡¹Ö"¿¡ ÁÖ·Î ¾²ÀδÙ.

  ÀÚ¹Ù´Â À¥ ºê¶ó¿ìÀú³»¿¡¼­ ½ÇÇàµÇ´Â GUIÀ» °³¹ßÇϴµ¥ ´õ¿í ÀûÇÕÇÑ
  Ç÷§Æû¿¡ µ¶¸³µÈ ¾ð¾îÀÌÁö¸¸ ¸Å¿ì ´À¸®°Ô ½ÇÇàµÈ´Ù. C++ and HTML, DHTML
  °ú ´õºÒ¾î Fast-CGI¸¦ »ç¿ëÇÏ´Â°Ô ´õ ³ªÀº ¼º´ÉÀ» ¹ßÈÖÇϱâÀ§Çؼ­´Â C++
  and HTML, DHTML °ú ´õºÒ¾î Fast-CGI¸¦ »ç¿ëÇÏ´Â°Ô ¹Ù¶÷Á÷ÇÏ´Ù.

  2.  ´Ù¿î·Îµå mychar

  ¸ðµç ÇÁ·Î±×·¥µé°ú ¿¹Á¦µéÀº ÀÌ ¹®¼­ÀÇ Ã·ºÎ¿¡ ÀÖ´Ù. ¿©·¯ºÐÀº ÇÑ°³ÀÇ tar
  zipÈ­ÀÏ·Î ´Ù¿î·Îµå ¹ÞÀ» ¼ö ÀÖ´Ù.  mychar class, libraries, ±×¸®°í ¿¹Á¦
  ÇÁ·Î±×·¥µéÀº ´ÙÀ½¿¡¼­ ´Ù¿î¹ÞÀ» ¼ö ÀÖ´Ù.

  o  ¿©±â" http://www.aldev.8m.com "°¡¼­ C++Programming howto.tar.gz
     file ¸¦ Ŭ¸¯ÇϽÿÀ.

  o  Mirror site :  <http://aldev.webjump.com>

  3.  mychar classÀÇ »ç¿ë

  ÀÖ´Ù. ¿©·¯ºÐÀº 'libmychar.a' ¸¦  includeÇØ¾ß ÇÏ°í  library ¸¦ "C++"
  libraryµéÀÌ À§Ä¡ÇÑ /usr/lib directory¿¡ Ä«ÇÇÇؾßÇÑ´Ù ('libmychar.a'´Â
  ``Appendix H''¿¡ ÀÖ´Â makefile¿¡¼­ ¸¸µé ¼ö ÀÖ´Ù ). 'libmychar.a'À»
  »ç¿ëÇϱâ â À§Çؼ­´Â ¿©·¯ºÐÀÇ ÇÁ·Î±×·¥À»  ´ÙÀ½°ú °°ÀÌ  ÄÄÆÄÀÏÇϽÿÀ.

  ______________________________________________________________________
          g++ example.cpp -lmychar
  ______________________________________________________________________

  ´ÙÀ½ »ùÇÃÄڵ带 º¸½Ã¿À.

  ______________________________________________________________________
          mychar aa;

          aa = " Washington DC is the capital of USA ";

          // You can use aa.val like a 'char *' variable in programs !!
          for (unsigned long tmpii = 0; tmpii < aa.length(); tmpii++)
          {
                  fprintf(stdout, "aa.val[%ld]=%c ", tmpii, aa.val[tmpii]);
          }

          // Using pointers on 'char *' val ...
          // Note: You must use a temporary local variable and assign the
          // pointer to aa.val. If you directly use aa.val and when
          // aa.val is incremented with aa.val++, then aa will go
          // call destructor and later when aa.val is accessed that
          // will cause core dump !!
          for (char *tmpcc = aa.val; *tmpcc != 0; tmpcc++)
          {
                  // MUST use temporary variable tmpcc !! See note above.
                  fprintf(stdout, "aa.val=%c ", *tmpcc);
          }
  ______________________________________________________________________

  mychar class ¸¦ Á¤ÀÇÇÑ  ¿ÏÀüÇÑ ¿¹Á¦ ÇÁ·Î±×·¥ "example_mychar.cpp" Àº
  ``Appendix A''¿¡ ÀÖ°í mychar class ´Â ``Appendix B''¿¡ ÀÖ´Ù.

  3.1.  ¿¬»êÀÚµé

  o  Equal to ==

  o  Not equal to !=

  o  Assignment =

  o  Add to itself and Assignment +=

  o  String concatenation or addition +

     ¿¬»êÀÚµéÀ» »ç¿ëÇÑ ¿¹Á¦

     ___________________________________________________________________
             mychar aa;
             mychar bb("Bill Clinton");

             aa = "put some value string";  // assignment operator
             aa += "add some more"; // Add to itself and assign operator
             aa = "My name is" + " Alavoor Vasudevan "; // string cat operator

             if (bb == "Bill Clinton")  // boolean equal to operator
                     cout << "bb is eqaul to 'Bill Clinton' " << endl;

             if (bb != "Al Gore")   // boolean 'not equal' to operator
                     cout << "bb is not equal to 'Al Gore'" << endl;
     ___________________________________________________________________

  3.2.  ÇÔ¼öµé

  o  ÇöÀç ¹®ÀÚ¿­ ±æÀÌ length()

  o  ¹®ÀÚ¿­ ¿ÞÂÊ À߶󳻱â. óÀ½¿¡ ³ª¿À´Â °ø¹é-»õÁÙ, ÅÜ-Á¦°ÅÇϱâ ltrim()

  o  ¹®ÀÚ¿­ ¿À¸¥ÂÊ À߶󳻱â. µû¶ó³ª¿À´Â °ø¹é-»õÁÙ, ÅÜ- Á¦°ÅÇϱâ rtrim()

  o  óÀ½°ú ³ªÁß¿¡ ³ª¿À´Â °ø¹é Á¦°ÅÇϱâ trim()

  o  µû¶ó³ª¿À´Â »õÁÙ Á¦°ÅÇϱâ chop()

  o  ¹®ÀÚ¿­À» ´ë¹®ÀÚ·Î ¹Ù²Ù±â  to_upper()

  o  ¹®ÀÚ¿­À» ¼Ò¹®ÀÚ·Î ¹Ù²Ù±â  to_lower()

  o  ½Ç¼ö°ªµéÀ» ¹Ý¿Ã¸²Çϰųª ³»¸²Ç챉  roundf(float input_val, short
     precision)

  o  double°ªµéÀ» ¹Ý¿Ã¸²Çϰųª ³»¸²Çϱâ roundd(double input_val, short
     precision)

  o  startÀ§Ä¡¿¡¼­ºÎÅÍ ¹®ÀÚ¿­ substr°ú ÀÏÄ¡ÇÏ´Â À§Ä¡ ã¾ÆÁÖ±â pos(char
     *substr, unsigned long start)

  o  Explodes the string and returns the list in the list-head pointer
     explodeH explode(char *seperator)

  o  Implodes the strings in the list-head pointer explodeH and returns
     the mychar variable implode(char *glue)

  o  ¸®½ºÆ® Çìµå Æ÷ÀÎÅÍ explodeHÀÇ ¹®ÀÚ¿­À» ºÙÀÌ°í mychar º¯¼ö¹Ýȯ
     join(char *glue)
  o  ÀÔ·Â ¹®ÀÚ¿­À» n¹ø ¹Ýº¹ repeat(char *input, unsigned int multiplier)

  o  ¹®ÀÚ¿­ÀÇ ±ÛÀÚ¸¦ ¿ª¼øÀ¸·Îreverse()

  o  ¹®ÀÚ¿­ ¡®needle¡¯À» °ÇÃÊ´õ¹Ì ¡®val¡¯¿¡¼­ ã¾Æ ¡®str¡¯·Î ¹Ù²Ù±â
     replace(char *needle, char *str)

  o  Char¸¦ ¹ø¿ª str_tr(char *from, char *to)

  o  ÅؽºÆ® ¹®ÀÚ¿­À» Áß¾Ó¿¡ center(int length, char padchar =

  o  ¿ø·¡ ¹®ÀÚ¿­ÀÇ °ø¹é¹®ÀÚ¸¦ ¡®number¡¯°³ÀÇ ¡®padchar¡¯·Î ¹Ù²Ù¾î ÁØ´Ù.
     ¸Ç ¾Õ°ú µÚÀÇ °ø¹éÀº Ç×»ó Á¦°ÅµÈ´Ù. ¸¸¾à ¡®number¡¯°¡ ¾ø°Å³ª 0À̸é,
     ¹®ÀÚ¿­ ¾ÈÀÇ ¸ðµç °ø¹éÀÌ Á¦°ÅµÈ´Ù.¡®number¡¯ÀÇ ±âº»°ªÀº 0ÀÌ°í
     ¡®padchar¡¯ÀÇ ±âº»°ªÀº ¡®¡¯. space(int number = 0, char padchar = '

  o  ¡®start¡¯¿Í ¡¯end¡¯¸¦ Æ÷ÇÔÇÑ ¸ðµç ¹®ÀÚµé·Î ÀÌ·ç¾îÁø ¹®ÀÚ¿­ ¹Ýȯ
     xrange(char start, char end)

  o  ¡®list¡¯¿¡ µé¾î ÀÖ´Â ¸ðµç ¹®ÀÚ Á¦°Å. ¡®list¡¯ÀÇ ±âº»¹®ÀÚ´Â °ø¹é¹®ÀÚ
     ¡® ¡¯ compress(char *list)

  o  ¡®start¡¯ À§Ä¡¿¡¼­ºÎÅÍ ¡®length¡¯°³ ¹®ÀÚ¸¦ ¹®ÀÚ¿­¿¡¼­ Á¦°Å. ¸¸¾à
     ¡®statr¡¯°¡ ¹®ÀÚ¿­ ±æÀ̺¸´Ù ´õ ±æ¸é ¹®ÀÚ¿­Àº º¯ÇÏÁö ¾Ê´Â´Ù.
     delstr(int start, int length)

  o  ¡®start¡¯¿¡¼­ ºÎÅÍ ¡®newstr¡¯¸¦ val¿¡ »ðÀÔÇÑ´Ù. ¡®newstr¡¯Àº
     ¡®length¡¯°³ ¹®ÀÚ·Î ¸ÂÃçÁø´Ù. ±âº» ¡®length¡¯´Â newstrÀÇ ¹®ÀÚ¿­
     ±æÀÌ insert(char *newstr, int start = 0, int length = 0, char
     padchar =  ')

  o  Val¾ÈÀÇ °¡Àå ¿ÞÂÊ¿¡ ÀÖ´Â ¡®length¡¯°³ÀÇ ¹®ÀÚ¿­À» ¹Ýȯ. ¹®ÀÚ¿­ ¿ÞÂÊ
     ÁÙ¸ÂÃ߱⿡ ºü¸¥ ¹æ¹ý left(int length = 0, char padchar = ' ')

  o  Val¾ÈÀÇ °¡Àå ¿À¸¥ÂÊ¿¡ ÀÖ´Â ¡®length¡¯°³ÀÇ ¹®ÀÚ¿­À» ¹Ýȯ. ¹®ÀÚ¿­
     ¿À¸¥ÂÊ ÁÙ¸ÂÃ߱⿡ ºü¸¥ ¹æ¹ý right(int length = 0, char padchar = '

  o  ¡®newstr¡¯°¡ val¾È¿¡ ¡®start¡¯¿¡¼­ ºÎÅÍ µ¤¾î ¾º¿©Áø´Ù. ¡®newstr¡¯Àº
     ¡®length¡¯°³ÀÇ ¹®ÀÚ·Î ¸ÂÃçÁø´Ù. ±âº» ¡®length¡¯Àº newstrÀÇ ±æÀÌ
     overlay(char *newstr, int start = 0, int length = 0, char padchar =
     ' ')

  o  ¹®ÀÚ¿­Áß ºÎºÐÀÇ »©³½´Ù. substr(int start, int length = 0)

  o  regx¶û óÀ½ ÀÏÄ¡ÇÏ´Â °÷À» ã´Â´Ù. at(char *regx)

  o  Regx¾ÕÀÇ ¹®ÀÚ¿­À» ¹Ýȯ before(char *regx)

  o  RegxeµÚÀÇ ¹®ÀÚ¿­À» ¹Ýȯ after(char *regx)

  o  ¹®ÀÚ¿­ÀÌ NULLÀ̸é Âü°ª ¹Ýȯ isnull()

  o  ¹®ÀÚ¿­À» NULL·Î clear()

  3.3.  ±âŸ ÇÔ¼öµé

  ±âŸ mychar ÇÔ¼öµéÀ» ¿©±â¿¡ ¸ð¾ÆµÎ¾ú´Ù. ÇÏÁö¸¸ À̰͵éÀ» »ç¿ëÇÏÁö´Â
  ¸¶¶ó.  ´ë½Å '+', '+=', '==' µî°ú °°Àº ¿¬»êÀÚµéÀ» »ç¿ëÇ϶ó. À̰͵éÀº
  'mychar' class 'private'¸â¹öµéÀÌ´Ù.

  o  Copy string str_cpy(char *bb)

  o  Long integer converted to string str_cpy(unsigned long bb)

  o  Integer converted to string str_cpy(int bb)

  o  Float converted to string str_cpy(float bb)

  o  String concatenate a char * str_cat(char *bb)

  o  String concatenate a int str_cat(int bb)

  o  String concatenate a int str_cat(unsigned long bb)

  o  String concatenate a float str_cat(float bb)

  o  Is equal to mychar ? bool equalto(const mychar & rhs, bool type =
     false)

  o  Is equal to char* ? bool equalto(const char *rhs, bool type =
     false)

     ¿¹¸¦ µé¾î Á¤¼ö¸¦ ¹®ÀÚ¿­·Î ¹Ù²Ù±â À§Çؼ­´Â ´ÙÀ½°ú °°ÀÌ Ç϶ó.

     ___________________________________________________________________
             mychar  aa;

             aa = 34;  //¿¬»êÀÚ ¡®=¡¯ ´Â int À» string ·Î ¹Ù²Û´Ù.
             cout << "The value of aa is : " << aa.val << endl;

             aa = 234.878; // ¿¬»êÀÚ '=' ´Â float À» string·Î ¹Ù²Û´Ù.
             cout << "The value of aa is : " << aa.val << endl;

             aa = 34 + 234.878;
             cout << "The value of aa is : " << aa.val << endl;
             // aa ´Â '268.878' ·Î µÈ´Ù.
             // mychar¸¦ cast ÇØ¾ß ÇÑ´Ù.
             aa = (mychar) 34 + " Honourable President Ronald Reagan " + 234.878;
             cout << "The value of aa is : " << aa.val << endl;
             // '34 Honourable President Ronald Reagan 234.878' ·Î Ãâ·ÂµÈ´Ù.
     ___________________________________________________________________

  4.  C++ Zap (Delete) ¸í·É¾î

  C++ ÀÇ delete °ú new ¸í·É¾î´Â "C"ÀÇ malloc °ú free ÇÔ¼öº¸´Ù ÈξÀ ³´´Ù.
  malloc °ú free ´ë½Å¿¡  new ¿Í zap (delete) ¸í·É¾î¸¦ °¡´ÉÇÑ ¸¹ÀÌ ¾²µµ·Ï
  ÇÏÀÚ.  delete¸í·É¾î¸¦ ´õ È®½ÇÈ÷ »ç¿ëÇϱâ À§Çؼ­ Zap() ¸í·É¾î¸¦ ¸¸µéÀÚ.
  zap() ¸í·É¾î´Â ´ÙÀ½°ú °°ÀÌ Á¤ÀÇµÉ ¼ö ÀÖ´Ù.

  ______________________________________________________________________
  /*
  **¿Ïº®ÇÏ°í Æ°Æ°ÇÑ ¸ÅÅ©·Î¸¦ ¸¸µé±â À§ÇØ do while À» »ç¿ëÇÑ´Ù.
  **¿¹¸¦ µé¾î, ¸¸¾à "do-while"À» ¾²Áö ¾ÊÀ¸¸é, ´ÙÀ½°ú °°ÀÌ µÉ
  **°ÍÀÌ´Ù
  ** if (bbint == 4)
  **              aa = 0
  ** else
  **              zap(aptr); //¹®Á¦¹ß»ý! aptrÀÌ Ç×»ó NULL·Î µÉ °ÍÀÌ´Ù
  */

  #define zap(x) do { delete(x); x = NULL; } while (0)
  ______________________________________________________________________

  ÀÚ ÀÌÁ¦ ¸ðµç Æ÷ÀÎÅ͵éÀÌ ³Î Æ÷ÀÎÅÍ·Î »ý¼ºµÈ´Ù°í °¡Á¤À» ÇÑ´Ù¸é ÀÏ·ÃÀÇ
  zap() ¸í·É¾î·Î ´ÙÀ½°ú °°ÀÌ new·Î »ý±ä°ÍµéÀ» ¾ÈÀüÇÏ°Ô »èÁ¦ ÇÒ ¼ö ÀÖ°í
  ¾ÆÁ÷ new·Î »ý±âÁö ¾ÊÀº °ÍµéÀ» Áö¿ìÁö ¾ÊÀ» ¼ö ÀÖ´Ù. ¿¹¸¦ µé¾î,

  ______________________________________________________________________
          zap(pFirstname);
          zap(pFirstname); // no core dumps !! Because pFirstname is NULL now
          zap(pFirstname); // no core dumps !! Because pFirstname is NULL now

          zap(pLastname);
          zap(pJobDescription);
  ______________________________________________________________________

  ÀÌ°ÍÀº ÀüÇô ½Å±âÇÑ °ÍÀÌ ¾Æ´Ï´Ù. ÀÌ°ÍÀº ´ÜÁö ¹Ýº¹µÇ´Â Äڵ带 ¼¼À̺êÇÏ°í
  ´õ Àбâ ÁÁ°Ô ¸¸µå´Â °ÍÀÌ´Ù. zap() ¸í·É¾î¿¡¼­  typecast¿¡ ÁýÂøÇÏÁö ¸¶¶ó
  - ¸¸¾à zap() ¸í·É¾î À§¿¡¼­ ¹º°¡ ¿¡·¯°¡ »ý±â¸é ±×°Ç ¾îµò°¡¿¡¼­ ´Ù¸¥
  ¿¡·¯°¡ ÀÖÀ» °¡´É¼ºÀÌ Å©±â ¶§¹®ÀÌ´Ù.  ¶ÇÇÑ ``my_malloc()'' , my_real­
  loc() ±×¸®°í my_free()´Â ´õ ±ú²ýÇÏ°í additional checksÀÌ Àֱ⶧¹®¿¡
  malloc(), realloc() and free(), ´ë½Å¿¡ »ç¿ëµÇ¾î¾ß ÇÑ´Ù. ¿¹¸¦ µé¾î
  ``my_malloc()'' °ú my_free() ÇÔ¼ö¸¦ »ç¿ëÇÑ mychar.h" º¸¶ó.  ÁÖÀÇ:
  'new' ·Î ÀâÇôÁø ¸Þ¸ð¸®À» free()·Î Ç®°Å³ª ¶Ç´« mallocÀ¸·Î ÀâÇôÁø
  ¸Þ¸ð¸®¸¦ 'delete' Ç®Áö¸¶¶ó. ÀÌ·Ä °æ¿ì °á°ú¸¦ ¿¹ÃøÇÒ ¼ö ¾ø´Ù.

  5.  my_malloc °ú my_freeÀÇ »ç¿ë

  malloc °ú reallocÀ» ÇÇÇÏ°í °¡´ÉÇÑ ÇÑ new and zap(delete)À» ¸¹ÀÌ ¾²µµ·Ï
  ÇÏÀÚ. ÇÏÁö¸¸ °¡²ûÀº "C++"¿¡¼­ "C" ½ºÅ¸ÀÏÀÇ ¸Þ¸ð¸® ¾ó·ÎÄÉÀ̼ÇÀ» ½á¾ßÇÒ
  ÇÊ¿ä°¡ ÀÖÀ» ¼öµµ ÀÖ´Ù. ÇÔ¼ö my_malloc() , my_realloc() and my_free()¸¦
  ½á¶ó. ÀÌ ÇÔ¼öµéÀº allocations °ú initialisationsÀ» ÀûÀýÈ÷ ÇÏ°í ¸Þ¸ð¸®
  ¹®Á¦µéÀ» ¹æÁöÇÑ´Ù. ¶ÇÇÑ ÀÌ ÇÔ¼öµéÀº (DEBUG ¸ðµå¿¡¼­) ¾ó·ÎÄÉÀÌÆ®µÈ
  ¸Þ¸ð¸®¸¦ ÃßÀûÇÏ°í ÇÁ·Î±×·¥ÀÌ ½ÇÇàµÇ±â Àü°ú ÈÄÀÇÃÑ ¸Þ¸ð¸® »ç¿ëÀ»
  ÇÁ¸°Æ®ÇÑ´Ù. ÀÌ°ÍÀº ¿©·¯ºÐ¿¡°Ô ¸Þ¸ð¸® À¯ÃâÀÌ ÀÖ´ÂÁöÀÇ ¿©ºÎ¸¦ ¾Ë·ÁÁØ´Ù.
  my_malloc °ú my_realloc Àº ¾Æ·¡¿Í °°ÀÌ Á¤ÀǵȴÙ. ÀÌ°ÍÀº Á¶±Ý ´õ ¸¹Àº
  ¸Þ¸ð¸®(SAFE_MEM = 5) ¸¦ ÇÒ´çÇÏ°í °ø°£À» ÃʱâÈ­ÇÑ´Ù. ±×¸®°í ¸¸¾à¿¡
  ÇÁ·Î±×·¥¾È¿¡ ÀÌ¹Ì ÇÒ´çÀÌ µÇ¾î ÀÖÀ¸¸é ÇÒ´çÀÌ µÇÁö ¾Ê´Â´Ù.
  'call_check(), remove_ptr()' ÇÔ¼ö´Â ¿ÀÁ÷ DEBUG°¡ makefile¿¡¼­ Á¤ÀÇ
  µÇ¾úÀ»¶§¿¡¸¸ ÀÛµ¿ÀÌ µÇ°í ÀÌ ÇÔ¼öµéÀº  ((void)0) ( Áï NULL for non-
  debug production release.)  ¿¡ assigned µÈ´Ù.  ±×µéÀº »ç¿ëµÈ ÃÑ
  ¸Þ¸ð¸®¸¦ ÃßÀûÇÏ´Â °ÍÀ» °¡´ÉÄÉ ÇÑ´Ù.

  ______________________________________________________________________
  void *local_my_malloc(size_t size, char fname[], int lineno)
  {
          size_t  tmpii = size + SAFE_MEM;
          void *aa = NULL;
          aa = (void *) malloc(tmpii);
          if (aa == NULL)
                  raise_error_exit(MALLOC, VOID_TYPE, fname, lineno);
          memset(aa, 0, tmpii);
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  char *local_my_realloc(char *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpjj = 0;
          if (aa) // aa !=  NULL
                  tmpjj = strlen(aa);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (char) * (tmpqq);
          aa = (char *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);

          // do not memset!! memset(aa, 0, tmpii);
          aa[tmpqq-1] = 0;
          unsigned long kk = tmpjj;
          if (tmpjj > tmpqq)
                  kk = tmpqq;
          for ( ; kk < tmpqq; kk++)
                  aa[kk] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }
  ______________________________________________________________________

  my_malloc ÇÁ·Î±×·¥ÀÇ full implementation À» À§Çؼ­ my_malloc.cpp. ¿Í
  Çì´õ È­ÀÏ my_malloc.h. À» º¸¶ó.  my_malloc °ú my_free »ç¿ë¿¹´Â ´ÙÀ½°ú
  °°´Ù.

  ______________________________________________________________________
          char    *aa;
          int     *bb;
          float   *cc;
          aa = (char *) my_malloc(sizeof(char)* 214);
          bb = (int *) my_malloc(sizeof(int) * 10);
          cc = (float *) my_malloc(sizeof(int) * 20);

          aa = my_realloc(aa, sizeof(char) * 34);
          bb = my_realloc(bb, sizeof(int) * 14);
          cc = my_realloc(cc, sizeof(float) * 10);
  ______________________________________________________________________

  my_realloc ¿¡¼­´Â º¯¼ö ÀÚü°¡ Àü´ÞµÇ°í, Á¤È®ÇÑ my_realloc ÀÌ
  ºÒ·ÁÁö±â¶§¹®¿¡ (Áï ÀûÀýÇÑ µ¥ÀÌŸ ŸÀÔ Æ÷ÀÎÅÍ°¡ ¹ÝȯµÇ±â¶§¹®¿¡)
  µ¥ÀÌŸŸÀÔÀ» º¯È¯ÇÒ ÇÊ¿ä°¡ ¾ø´Ù´Â °ÍÀ» ÁÖÁöÇ϶ó. my_reallocÀº char*,
  int* ±×¸®°í float*¸¦ À§ÇÑ Áߺ¹µÈ(overloaded) ÇÔ¼öµéÀ» °®°í ÀÖ´Ù.

  6.  Debug È­Àϵé

  C++ À̳ª C ÇÁ·Î±×·¥À» µð¹ö±×ÇÏ·Á¸é debug.h È­ÀÏÀ» include½ÃÅ°°í
  debug.h ÇÔ¼ö¸¦ ¿¬°á½ÃÅ°µµ·Ï 'Makefile' ¾È¿¡¼­ DEBUG¸¦  Á¤ÀÇÇضó.
  '-DDEBUG' ¸¦ »èÁ¦Çϸé debug ÇÔ¼ö calls´Â ((void)0) i.e. NULL·Î µÈ´Ù.
  ±×·¯¹Ç·Î ÇÁ·ÎÁ§Æ®ÀÇ ÃÖÁ¾ production release ¹öÀü¿¡ ¾Æ¹«·± ¿µÇâÀ»
  ³¢Ä¡Áö ¾Ê´Â´Ù.  ¿©·¯ºÐÀº ÇÁ·Î±×·¥¿¡¼­ debug ÇÔ¼öµéÀ» ¸¶À½´ë·Î »ç¿ëÇÒ
  ¼ö ÀÖÀ¸¸ç production ½ÇÇàÈ­ÀÏÀÇ Å©±â¸¦ Áõ°¡½ÃÅ°Áö ¾Ê´Â´Ù.

  debug ·çƾÀÇ ±¸ÇöÀ» º¸·Á¸é``debug.cpp'' ±×¸®°í debug.h ¿Í debug ÇÔ¼ö¸¦
  »ç¿ëÇÑ »ùÇÃÀ» º¸±âÀ§Çؼ­´Â ``my_malloc.cpp'' È­ÀÏÀ» º¸¶ó.  »ùÇÃ
  ``Makefile'' À» º¸¶ó.

  7.  C++ Online ¹®¼­µé

  ´ÙÀ½ÀÇ C++ »çÀÌÆ®µéÀ» ¹æ¹®ÇØ º¸¶ó. :-

  o  C++ Crash-proof site
     <http://www.troubleshooters.com/codecorn/crashprf.htm>

  o  C++ Memory site
     <http://www.troubleshooters.com/codecorn/memleak.htm>

     ÀÎÅͳݿ¡´Â ¼ö¸¹Àº C++ °ü·Ã ¹®¼­µéÀÌ ÀÖ´Ù. Yahoo, Lycos, Infoseek,
     ±×¸®°í Excite ¿Í °°ÀÎ ¼­Ä¡¿£Áø¿¡ °¡¼­ 'C++ tutorials' 'C++
     references' 'C++ books' À» Å°¿öµå·Î ŸÀÔÀ» Çϸé ãÀ» ¼ö ÀÖ´Ù.
     Advanced search ¸¦ Ŭ¸¯Çؼ­ ¼­Ä¡ °á°úÀÇ ºÐ·ù¸¦ Á¼Èú ¼öµµ ÀÖ°í
     ¾îÈÖ³ª ±¸ÀýÀ» Á¤È®È÷ ½á¼­ ¼­Ä¡ÇÒ ¼öµµ ÀÖ´Ù.

  o  <http://www.yahoo.com>

  o  <http://www.lycos.com>

  o  <http://www.infoseek.com>

  o  <http://www.excite.com>

  o  <http://www.mamma.com>

  7.1.  C++ Æ©Å͸®¾óµé

  ÀÎÅͳݿ¡ »ç¿ë°¡´ÉÇÑ  ¸¹Àº ¿Â¶óÀÎ Æ©Å͸®¾óµéÀÌ ÀÖ´Ù. ¼­Ä¡ ¿£Áø¿¡¼­
  'C++ tutorials' ¸¦ ŸÀÔÇؼ­ ãÀ» ¼ö ÀÖ´Ù.

  7.2.  C++ ÄÚµù Ç¥ÁØ

  ´ÙÀ½°ú °°Àº C++ ÄÚµù URLµéÀ» °¡ º¸ÀÚ.

  o  C++ coding standard
     <http://www.cs.umd.edu/users/cml/cstyle/CppCodingStandard.html>

  o  Coding standards from Possibility
     <http://www.possibility.com/Cpp/CppCodingStandard.html>

  o  Coding standards from Ambysoft
     <http://www.ambysoft.com/javaCodingStandards.html>

  o  Rules and recommendations
     <http://www.cs.umd.edu/users/cml/cstyle/>

  o  Indent and annotate
     <http://www.cs.umd.edu/users/cml/cstyle/indhill-annot.html>

  o  Elemental rules  <http://www.cs.umd.edu/users/cml/cstyle/Ellemtel-
     rules.html>

  o  C++ style doc  <http://www.cs.umd.edu/users/cml/cstyle/Wildfire-
     C++Style.html>

  7.3.  C++ Äü ·¹ÆÛ·±½º

  ¼­Ä¡¿£Áø¿¡¼­ 'C++ Reference' ¸¦ ŸÀÔÇؼ­ ãÀ» ¼ö ÀÖ´Ù.

  7.4.  C++ À¯Áî³Ý ´º½º±×·ìµé

  o  C++ newsgroups :  <comp.lang.c++.announce>

  o  C++ newsgroups :  <comp.lang.c++.*>

  8.  ¸Þ¸ð¸® µµ±¸µé

  ´ÙÀ½ÀÇ ¸Þ¸ð¸® µð¹ö±ë µµ±¸µéÀ» »ç¿ëÇÒ ¼ö ÀÖ´Ù.

  o  ¸®´ª½º contrib cdrom¿¡ ´ëÇؼ­´Â mem_test*.rpm ÆÑÅ°Áö¸¦ º¸¸é µÈ´Ù.

  o  ¸®´ª½º ½Ãµð·Ò¿¡ ´ëÇؼ­´Â ElectricFence*.rpm ÆÑÅ°Áö¸¦ º¸¸é µÈ´Ù.

  o  Purify Tool from Rational Software Corp  <http://www.rational.com>

  o  Insure++ Tool from Parasoft Corp  <http://www.parasoft.com>

  o  Linux Tools at  <http://www.xnet.com/~blatura/linapp6.html#tools>

  o  Yahoo, Lycos, Excite, ȤÀº Mamma.com °ú °°Àº ÀÎÅÍ³Ý ¼­Ä¡¿£Áø¿¡¼­
     "Linux memory debugging tools"À» Å°¿öµå·Î ŸÀÔÀ» Çؼ­ ã¾Æº¸¸é µÈ´Ù

  9.  °ü·Ã URLµé

  C, C++ °ú °ü·ÃµÈ ´ÙÀ½ÀÇ ÀÎÅÍ³Ý »çÀÌÆ®¸¦ ¹æ¹®ÇØ º¸ÀÚ.

  o  Vim color text editor for C++, C
     <http://metalab.unc.edu/LDP/HOWTO/Vim-HOWTO.html>

  o  C++ Beautifier HOWTO  <http://metalab.unc.edu/LDP/HOWTO/C-
     C++Beautifier-HOWTO.html>

  o  CVS HOWTO for C++ programs  <http://metalab.unc.edu/LDP/HOWTO/CVS-
     HOWTO.html>

  o  Linux goodies main site  <http://www.aldev.8m.com>

  o  Linux goodies mirror site  <http://aldev.webjump.com>

  10.  ÀÌ ¹®¼­ÀÇ ´Ù¸¥ Æ÷¸äµé

  ÀÌ ¹®¼­´Â 10¿©Á¾ÀÇ ´Ù¸¥ Æ÷¸ä -DVI, Æ÷½ºÆ®½ºÅ©¸³Æ®, ·¹ÀÌÅؽº, LyX, GNU-
  info, HTML, RTF(Rich Text Format), Plain-text, Unix man pages ±×¸®°í
  SGML - À¸·Î ³ª¿Ô´Ù.

  o  ÀÌ  HOWTO ¹®¼­´Â HTML, DVI, Postscript ȤÀº SGML Æ÷¸äÀ¸·Î µÈ ÇÑ°³ÀÇ
     tarÈ­ÀÏ·Î ´ÙÀ½¿¡¼­ º¼ ¼ö ÀÖ´Ù.
     <ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/other-formats/> or
     <ftp://metalab.unc.edu/pub/Linux/docs/HOWTO/other-formats/>

  o  Plain text Æ÷¸äÀº:  <ftp://metalab.unc.edu/pub/Linux/docs/HOWTO> or
     <ftp://metalab.unc.edu/pub/Linux/docs/HOWTO>

  o  ºÒ¾î³ª µ¶ÀϾî, ½ºÆäÀξî, Áß±¹¾î ÀϺ»¾î¿Í °°Àº ¿Ü±¹¾î·Î ¹ø¿ªµÈ °ÍÀº
     <ftp://metalab.unc.edu/pub/Linux/docs/HOWTO> or
     <ftp://metalab.unc.edu/pub/Linux/docs/HOWTO> ¿¡¼­ º¼ ¼ö ÀÖ´Ù.
     ¹ø¿ªÀ» µµ¿Í ÁÖ°íÀÚ ÇÏ´Â »ç¶÷Àº ´©±¸³ª ȯ¿µÇÑ´Ù.

     À̹®¼­´Â "SGML" ÅøÀ» ÀÌ¿ëÇؼ­ ¾²¿©Á³À¸¸ç,  "SGML" ÅøÀº The document
     is written using a tool called "SGML tool" which can be got from -
     <http://www.xs4all.nl/~cg/sgmltools/> ¿¡¼­ ±¸ÇÒ ¼ö ÀÖ´Ù. ¼Ò½º¸¦
     ÄÄÆÄÀÏ ÇÏ¸é ´ÙÀ½°ú °°Àº ¸í·É¾î¸¦ º¸°Ô µÉ °ÍÀÌ´Ù.

  o  sgml2html C++Programming-HOWTO.sgml     (to generate html file)

  o  sgml2rtf  C++Programming-HOWTO.sgml     (to generate RTF file)

  o  sgml2latex C++Programming-HOWTO.sgml    (to generate latex file)

  ÀÌ ¹®¼­´Â ´ÙÀ½¿¡ ÀÖ´Ù.

  o  <http://metalab.unc.edu/LDP/HOWTO/C++Programming-HOWTO.html>

  ¶ÇÇÑ ´ÙÀ½ÀÇ ¹Ì·¯ »çÀÌÆ®¿¡¼­ ÀÌ ¹®¼­¸¦ ãÀ» ¼ö ÀÖ´Ù.

  o  <http://www.caldera.com/LDP/HOWTO/C++Programming-HOWTO.html>

  o  <http://www.WGS.com/LDP/HOWTO/C++Programming-HOWTO.html>

  o  <http://www.cc.gatech.edu/linux/LDP/HOWTO/C++Programming-
     HOWTO.html>

  o  <http://www.redhat.com/linux-info/ldp/HOWTO/C++Programming-
     HOWTO.html>

  o  (³×Æ®¿öÅ© ÁּҸ鿡¼­) °¡±î¿î ´Ù¸¥ ¹Ì·¯ »çÀÌÆ®µéÀº
     <http://metalab.unc.edu/LDP/hmirrors.html> ¿¡¼­ ãÀ» ¼ö ÀÖ´Ù.
     »çÀÌÆ®¸¦ ¼±ÅÃÇÏ°í /LDP/HOWTO/C++Programming-HOWTO.html µð·ºÅ丮·Î
     °¡¸é µÈ´Ù.

  ÀÌ ¹®¼­¸¦ dvi Æ÷¸äÀ¸·Î º¸±âÀ§Çؼ­´Â  xdvi ÇÁ·Î±×·¥À» »ç¿ëÇÏ¸é µÈ´Ù.
  xdvi ÇÁ·Î±×·¥Àº  ·¹µåÇò ¸®´ª½ºÀÇ tetex-xdvi*.rpm ÆÑÅ°Áö ¾È¿¡ ÀÖÀ¸¸ç
  Á¦¾îÆÇ|ÀÀ¿ëÇÁ·Î±×·¥(Applications) | Publishing | TeX ¸Þ´º¹öÆ°À» ÅëÇؼ­
  ãÀ» ¼ö ÀÖ´Ù.

               dvi ¹®¼­¸¦ Àбâ À§Çؼ­´Â xdvi -geometry 80x90 howto.dvi ¶ó´Â
               ¸í·É¾î¸¦ ÁÖ¾î¾ß ÇÑ´Ù.
               ±×¸®°í ¸¶¿ì½º·Î À©µµ¿ìÀÇ Å©±â¸¦ Á¶ÀýÇÏ°í xdviÀÇ ¸ÞÀÎ ÆäÀÌÁö¸¦ º¸¸é
               µÈ´Ù.
               À§¾Æ·¡·Î ¿òÁ÷À̱â À§Çؼ­´Â È­»ìÇ¥ Å°³ª ÆäÀÌÁö ¾÷, ÆäÀÌÁö ´Ù¿îµîÀÇ
               Å°¸¦ »ç¿ëÇϰųª
               'f', 'd', 'u', 'c', 'l', 'r', 'p', 'n' ÀÇ ±ÛÀÚÅ°¸¦ À§·Î ¿Ã¸®°Å³ª
               ¾Æ·¡·Î Áß¾ÓÀ¸·Î ȤÀº ´ÙÀ½ ÆäÀÌÁö³ª ÀÌ
               Àü ÆäÀÌÁö·Î À̵¿Çϱâ À§Çؼ­ »ç¿ëÇÒ ¼öµµ ÀÖ´Ù.
               expert ¸Þ´º¸¦ ¾ø¾Ö·Á¸é 'x' ¸¦ ´©¸£¸é µÈ´Ù.

  È­ÀÏÀ» ÀÐÀ» ¼ö ÀÖ´Ù. °í½ºÆ®½ºÅ©¸³Æ® ÇÁ·Î±×·¥°ú gv ÇÁ·Î±×·¥Àº °¢°¢
  ·¹µåÇò ¸®´ª½ºÀÇ  ghostscript*.rpm ÆÑÅ°Áö¿¡ ÀÖ°í gv ÇÁ·Î±×·¥Àº gv*.rpm
  ÆÑÅ°Áö¿¡ ÀÖ°í, ControlPanel | Applications | Graphics ¸Þ´º¹öÆ°À»
  ÅëÇؼ­ À§Ä¡¸¦ ã¾Æ³¾ ¼ö ÀÖ´Ù. gv ÇÁ·Î±×·¥Àº °í½ºÆ®½ºÅ©¸³Æ®º¸´Ù
  »ç¿ëÀÚ°¡ Æí¸®Çϵµ·Ï ¸¸µé¾îÁ® ÀÖ´Ù. °í½ºÆ®½ºÅ©¸³Æ®¿Í gv´Â OS/2³ª À©µµ¿ì
  95 ±×¸®°í NT¿Í °°Àº ´Ù¸¥ Ç÷¿Æû¿¡¼­µµ »ç¿ë °¡´ÉÇÏ´Ù.

  o  Get ghostscript for Windows 95, OS/2, and for all OSes from
     <http://www.cs.wisc.edu/~ghost>

           Æ÷½ºÆ®½ºÅ©¸³Æ® ¹®¼­¸¦ ÀбâÀ§Çؼ­´Â
            gv howto.ps ¶ó´Â ¸í·É¾î¸¦ ¾´´Ù.
           °í½ºÆ®½ºÅ©¸³Æ®¸¦ »ç¿ëÇϱâ À§Çؼ­´Â
            ghostscript howto.ps ¸¦ ¾´´Ù.

  HTML Æ÷¸äÀÇ ¹®¼­´Â ³Ý½ºÄÉÀÌÇÁ ³×ºñ°ÔÀÌÅͳª ¸¶ÀÌÅ©·Î¼ÒÇÁÆ® ÀÎÅͳÝ
  ÀͽºÇ÷ξî, ·¹µåÇò ¹Ù·Ð À¥ ºê¶ó¿ìÀú ȤÀº ´Ù¸¥ À¥ ºê¶ó¿ìÀú¸¦ ½á¼­ ÀÐÀ»
  ¼ö ÀÖ´Ù latex, LyX ¹®¼­´Â LyX a "X-Windows" front end to latex À»
  ÀÌ¿ëÇØ ÀÐÀ» ¼ö ÀÖ´Ù.

  11.  ÀúÀÛ±Ç

  ÀúÀÛ±Ç Á¶Ç×Àº LDP (¸®´ª½º ¹®¼­ ÇÁ·ÎÁ§Æ®) ·Î¼­ GNU/GPL ÀÌ´Ù. LDP ´Â
  ÇϳªÀÇ GNU/GPLÇÁ·ÎÁ§Æ®ÀÌ´Ù. Ãß°¡·Î ¿ä±¸µÇ´Â °Íµé·Î¼­ ÀúÀÚÀÇ À̸§,
  À̸ÞÀÏ ÁÖ¼Ò, ±×¸®°í ¸ðµç º¹»çº»µé¿¡ ÀÌ ÀúÀÛ±Ç Á¶Ç׿¡ ´ëÇÑ ºÎºÐÀ»
  ³Ö¾îÁÖ¾î¾ß ÇÑ´Ù. ÀÌ ¹®¼­¸¦ Á¶±ÝÀÌ¶óµµ ¹Ù²Ù°Å³ª ¹º   Ãß°¡ÇÏ°Ô µÇ¸é ÀÌ
  ¹®¼­ÀÇ ¸ðµç ÀúÀڵ鿡°Ô ±×°ÍÀ» ¾Ë·ÁÁֱ⠹ٶõ´Ù.

  12.  ÷ºÎ A example_mychar.cpp

  ¸ðµç ÇÁ·Î±×·¥µéÀº Download mychar ·Î ºÎÅÍ ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå ¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¾òÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ 'Text'
  ŸÀÔÀ¸·Î ÀúÀåÀ» ÇÏ¸é µÈ´Ù.

  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ÀÌÁö¸¸ Ãß°¡·Î ¸ðµç º¹Á¦º»¿¡ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀ»
  //Æ÷ÇÔ½ÃÄÑÁÖ¾î¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************
  // ÄÄÆÄÀÏ ÇÏ·Á¸é( libmychar.a°¡ ÇöÀç µð·ºÅ丮¿¡ ÀÖ´Ù°í
  // °¡Á¤ÇÏ°í )
  //              g++ example_mychar.cpp -L. -lmychar

  #include <stdlib.h>  // for putenv
  #include "mychar.h"

  /////////////////////////////////////////////////
  //mychar »ç¿ë ¿¹Á¦ ÇÁ·Î±×·¥
  /////////////////////////////////////////////////

  int main(int argc, char **argv)
  {
          char p_name[1024];
          sprintf(p_name, "PROGRAM_NAME=%s", argv[0]);
          putenv(p_name);
          print_total_memsize(); // in the beginning
          mychar aa, bb;

          //bb.str_cpy("  bbSTRing  ");
          bb = "   bbSTRing   ";

          //+ ¿¬»êÀÚ Å×½ºÆ®Çϱâ
          //aa + " rhs "; //  ¿©±â¼­´Â ¾î¶² Ãâ·Âµµ °®Áö ¾Ê°Ô µÉ°ÍÀÌ´Ù !!
          //¹Ýµå½Ã ´ÙÀ½ÁÙ¿¡ ³ª¿À´Â °Í ó·³ Á÷Á¢ fprintf ¸¦ »ç¿ëÇØ¾ß ÇÑ´Ù.
          fprintf(stdout, "\n0) aa.val is :%sEOF\n", (aa + " my rhs " ).val);

          //=¿¬»êÀÚ Å×½ºÆ®Çϱâ
          aa = " lhs " ;
          fprintf(stdout, "0-1) With operator= aa.val is :%sEOF\n", aa.val);

          //+ ¿¬»êÀÚ Å×½ºÆ® Çϱâ
          //aa + " rhs "; //  ¿©±â¼­´Â ¾î¶² Ãâ·Âµµ °®Áö ¾Ê°Ô µÉ°ÍÀÌ´Ù !!
          //¹Ýµå½Ã ´ÙÀ½ÁÙ¿¡ ³ª¿À´Â °Í ó·³ Á÷Á¢ fprintf ¸¦ »ç¿ëÇØ¾ß ÇÑ´Ù.
          fprintf(stdout, "\n0) With lsh operator+, aa.val is :%sEOF\n", (" my lhs " + aa ).val);

          //aa.str_cpy(bb.val);
          aa = bb;
          aa.to_upper();
          fprintf(stdout, "1) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa.to_lower();
          fprintf(stdout, "2) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa.ltrim();
          fprintf(stdout, "3) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa.rtrim();
          fprintf(stdout, "4) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa.trim();
          fprintf(stdout, "5) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa = aa + " testing newlines \n\n\n\n";
          aa.chop();
          fprintf(stdout, "5-1) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa = aa + " rhs ";
          fprintf(stdout, "6) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa = " lhs " + aa;
          fprintf(stdout, "7) aa.val is :%sEOF\n", aa.val);

          // ¼ýÀÚ ´õÇϱ⠿¹Á¦
          //aa = (mychar) 9989 + "kkk" + 33 ;
          aa = 9999;
          fprintf(stdout, "7-1) aa.val is :%sEOF\n", aa.val);

          aa = bb;
          aa = " lhs " + aa + " rhs " + " 9989 " + " 33 ";
          fprintf(stdout, "8) aa.val is :%sEOF\n", aa.val);

          aa = " AA value ";
          aa = bb + "alkja " + " 99djd " ;
          fprintf(stdout, "9) aa.val is :%sEOF\n", aa.val);

          aa = " AA value ";
          aa = (mychar) "alkja " + " 99djd " ;
          fprintf(stdout, "10) aa.val is :%sEOF\n", aa.val);

          aa = " AA value ";
          aa += (mychar) " al dev test kkk... " + " al2 slkj" + " al3333 ";
          fprintf(stdout, "11) aa.val is :%sEOF\n", aa.val);

          aa = " AA value ";
          aa = aa + " add aa " + aa + aa + aa + " 1111 " + " 2222 " + aa + aa + aa + " 3333 ";
          fprintf(stdout, "12) aa.val is :%sEOF\n", aa.val);

          aa = "12345678";
          aa.reverse();
          fprintf(stdout, "13) aa.val is :%sEOF\n", aa.val);

          aa = " AA value ";
          aa = aa + " add aa " + aa + 1111 +" "+ 2222 + " " + 3.344 + aa;
          fprintf(stdout, "14) aa.val is :%sEOF\n", aa.val);

          aa.roundd(123456.0123456789012345, 13);
          fprintf(stdout, "15) double aa.val is :%sEOF\n", aa.val);

          aa.roundf(123456.0123456789, 13);
          fprintf(stdout, "16) float aa.val is :%sEOF\n", aa.val);

          // Test equal to operators
          aa = " AA value ";
          mychar cc(" AA value ");
          if (aa == cc)
                  fprintf(stdout, "\naa=%s and cc=%s are equal!!\n", aa.val, cc.val);
          else
                  fprintf(stdout, "\naa=%s and cc=%s are NOT equal!!\n", aa.val, cc.val);
          cc = "CC";
          if (aa == cc)
                  fprintf(stdout, "\naa=%s and cc=%s are equal!!\n", aa.val, cc.val);
          else
                  fprintf(stdout, "\naa=%s and cc=%s are NOT equal!!\n", aa.val, cc.val);
          if (aa == " AA value ")
                  fprintf(stdout, "\naa=%s and string are equal!!\n", aa.val);
          else
                  fprintf(stdout, "\naa=%s and string are NOT equal!!\n", aa.val);
          if (aa == " AA valuexxx ")
                  fprintf(stdout, "\naa=%s and string are equal!!\n", aa.val);
          else
                  fprintf(stdout, "\naa=%s and string are NOT equal!!\n", aa.val);

          //aa.val ¸¦ 'char *' º¯¼öó·³ ÇÁ·Î±×·¥¿¡¼­ »ç¿ëÇÒ ¼ö ÀÖ´Ù!!
          fprintf(stdout, "\n ");
          for (unsigned long tmpii = 0; tmpii < aa.length(); tmpii++)
          {
                  fprintf(stdout, "aa.val[%ld]=%c ", tmpii, aa.val[tmpii]);
          }
          fprintf(stdout, "\n");

          //'char *' val ...¿¡ Æ÷ÀÎÅÍ »ç¿ëÇϱâ
          fprintf(stdout, "\n ");

          for (char *tmpcc = aa.val; *tmpcc != 0; tmpcc++)
          {
                  // MUST use temporary var tmpcc !! See note above.
                  fprintf(stdout, "aa.val=%c ", *tmpcc);
          }
          fprintf(stdout, "\n");

          print_total_memsize(); // in the end
          exit(0);
  }
  ______________________________________________________________________

  13.  ÷ºÎ B mychar.h

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  'Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.

  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  //Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************

  //¸Þ¸ð¸®À¯ÃâÀ» ¹æÁöÇϱâÀ§Çؼ­´Â - a char class to manage character
  //variables
  //char[] ȤÀº char *´ë½Å  mychar ³ª string class ¸¦ »ç¿ëÇÏ´Â °ÍÀÌ ÁÁ´Ù.

  #ifndef __MYCHAR_H_
  #define __MYCHAR_H_

  //#include <iostream> // iostreamÀº ÇÁ·Î±×·¥ÀÌ Ä¿Áö´Ï±î »ç¿ëÇÏÁö ¾Ê´Â´Ù.
  //#include <stdlib.h> //free() ¿Ímalloc() ¸¦ ¾²±âÀ§ÇØ
  #include <string.h> // for strcpy()
  #include <ctype.h> // for isspace()
  #include <stdio.h> // for sprintf()
  #include <list.h> // for sprintf()
  #include <math.h> // for modf(), rint()

  #include "my_malloc.h"
  #include "debug.h" // debug_(name, value)  debug2_(name, value, LOG_YES)

  const short INITIAL_SIZE =      50;
  const short NUMBER_LENGTH = 70;

  // ÃÖ¼ÒÇÑÀÇ ÇÔ¼ö¿Í º¯¼ö¸¦ °¡Áø ÀÛÀº Ŭ·¡½º (class)
  // This class to be kept small... ÀÌ Å¬·¡½º´Â °è¼Ó ÀÛ°Ô À¯ÁöµÉ°ÍÀÌ´Ù.
  class mychar
  {
          public:
                  mychar();
                  mychar(char bb[]);  // needed by operator+
                  mychar(int bb);  // needed by operator+
                  mychar(unsigned long bb);  // needed by operator+
                  mychar(float bb);  // needed by operator+
                  mychar(double bb);  // needed by operator+
                  mychar(const mychar & rhs);  // Copy Constructor needed by operator+
                  ~mychar();

                  char *val;

                  unsigned long length() { return strlen(val); }

                  void ltrim();
                  void rtrim();
                  void trim();
                  void chop();

                  void to_upper();
                  void to_lower();

                  void roundf(float input_val, short precision);
                  void decompose_float(long *integral, long *fraction);

                  void roundd(double input_val, short precision);
                  void decompose_double(long *integral, long *fraction);

                  long pos(char substr[], unsigned long start);

                  void explode(char *seperator);
                  void implode(char *glue);
                  void join(char *glue);
                  void repeat(char *input, unsigned int multiplier);
                  void reverse();
                  void replace(char *needle, char *str);
                  void str_tr(char *from, char *to);
                  void center(int length, char padchar = ' ');
                  void space(int number = 0, char padchar = ' ');
                  void xrange(char start, char end);
                  void compress(char *list);
                  void delstr(int start, int length);
                  void insert(char *newstr, int start = 0, int length = 0, char padchar = ' ');
                  void left(int length = 0, char padchar = ' ');
                  void right(int length = 0, char padchar = ' ');
                  void overlay(char *newstr, int start = 0, int length = 0, char padchar = ' ');
                  mychar substr(int start, int length = 0);

                  mychar at(char *regx); // matches first match of regx
                  mychar before(char *regx); // returns string before regx
                  mychar after(char *regx); // returns string after regx

                  bool isnull();
                  void clear();

                  // All Operators ...
                  mychar operator+ (const mychar & rhs);
                  friend mychar operator+ (const mychar & lhs, const mychar & rhs);

                  mychar& operator+= (const mychar & rhs); // using reference will be faster
                  mychar& operator= (const mychar & rhs); // using reference will be faster
                  bool operator== (const mychar & rhs); // using reference will be faster
                  bool operator== (const char *rhs);
                  bool operator!= (const mychar & rhs);
                  bool operator!= (const char *rhs);

                  static  list<mychar>            explodeH;  // list head

          private:
                  //static mychar *global_mychar; // for use in add operator
                  //inline void free_glob(mychar **aa);
                  void str_cpy(char bb[]);
                  void str_cpy(int bb); // itoa
                  void str_cpy(unsigned long bb);
                  void str_cpy(float bb); // itof

                  void str_cat(char bb[]);
                  void str_cat(int bb);
                  void str_cat(unsigned long bb);
                  void str_cat(float bb);

                  bool equalto(const mychar & rhs, bool type = false);
                  bool equalto(const char *rhs, bool type = false);
  };
  // Global variables are defined in mychar.cpp

  #endif // __MYCHAR_H_
  ______________________________________________________________________

  14.  ÷ºÎ C mychar.cpp

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.

  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  //Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************

  //¹®ÀÚ¿­ Ŭ·¡½º³ª ÀÌ Å¬·¡½º¸¦ »ç¿ëÇÑ´Ù.
  //
  //¸Þ¸ð¸®À¯ÃâÀ» ¹æÁöÇϱâÀ§Çؼ­´Â - a char class to manage character
  //variables
  //char[] ȤÀº char *´ë½Å  mychar ³ª string class ¸¦ »ç¿ëÇÏ´Â °ÍÀÌ ÁÁ´Ù.

  // ´ÙÀ½°ú °°ÀÌ ÄÄÆÄÀÏ ÇÒ °Í
  //              g++ mychar.cpp

  #include "mychar.h"

  // Global variables ....
  //mychar *mychar::global_mychar = NULL; // global var
  list<mychar>            mychar::explodeH;

  mychar::mychar()
  {
          debug_("In cstr()", "ok");
          val = (char *) my_malloc(sizeof(char)* INITIAL_SIZE);
  }

  mychar::mychar(char *bb)
  {
          unsigned long tmpii = strlen(bb);
          val = (char *) my_malloc(sizeof(char)* tmpii);
          strncpy(val, bb, tmpii);
          val[tmpii] = '\0';

          //debug_("In cstr(char *bb) bb", bb);
          //debug_("In cstr(char *bb) val", val);
          #ifdef DEBUG
                  //fprintf(stderr, "\nAddress of val=%x\n", & val);
                  //fprintf(stderr, "\nAddress of this-pointer=%x\n", this);
          #endif // DEBUG
  }

  mychar::mychar(int bb)
  {
          val = (char *) my_malloc(NUMBER_LENGTH); // integers 70 digits max
          sprintf(val, "%d", bb);
  }

  mychar::mychar(unsigned long bb)
  {
          val = (char *) my_malloc(NUMBER_LENGTH); // long 70 digits max
          sprintf(val, "%lu", bb);
  }

  mychar::mychar(float bb)
  {
          val = (char *) my_malloc(NUMBER_LENGTH); // float 70 digits max
          sprintf(val, "%f", bb);
  }

  mychar::mychar(double bb)
  {
          val = (char *) my_malloc(NUMBER_LENGTH); // double 70 digits max
          sprintf(val, "%f", bb);
  }
  // Copy Constructor needed by operator +
  mychar::mychar(const mychar & rhs)
  {
          // Do a deep-copy instead of compiler's default shallow copy copy-cstr
          debug_("In copy-cstr()", "ok");
          unsigned long tmpii = strlen(rhs.val);
          val = (char *) my_malloc(sizeof(char)* tmpii);
          strncpy(val, rhs.val, tmpii);
          val[tmpii] = '\0';
  }

  mychar::~mychar()
  {
          //debug_("In dstr val", val);
          #ifdef DEBUG
                  //fprintf(stderr, "\nAddress of val=%x\n", & val);
                  //fprintf(stderr, "\nAddress of this-pointer=%x\n", this);
          #endif // DEBUG
          my_free(val);
          //delete [] val;
          val = NULL;
  }

  // MUST use pointer-to-pointer **aa, otherwise the argument
  // is NOT freed !!
  /*
  inline void mychar::free_glob(mychar **aa)
  {
          debug_("called free_glob()", "ok" );
          if (*aa != NULL)  // (*aa != NULL)
          {
                  debug_("*aa is not null", "ok");
                  delete *aa;
                  *aa = NULL;
          }
          //else
                  debug_("*aa is null", "ok");

          //if (*aa == NULL)
          debug_("*aa set to null", "ok");
  }
  */

  // Explodes the string and returns the list in
  // the list-head pointer explodeH
  void mychar::explode(char *seperator)
  {
          char *aa = NULL, *bb = NULL;
          aa = (char *) my_malloc(length());
          for (bb = strtok(aa, seperator); bb != NULL; bb = strtok(NULL, seperator) )
          {
                  mychar *tmp = new mychar(bb);
                  mychar::explodeH.insert(mychar::explodeH.end(), *tmp);
          }
          my_free(aa);

          list<mychar>::iterator iter1; // see file include/g++/stl_list.h
          debug_("Before checking explode..", "ok");
          if (mychar::explodeH.empty() == true )
          {
                  debug_("List is empty!!", "ok");
          }

          for (iter1 = mychar::explodeH.begin(); iter1 != mychar::explodeH.end(); iter1++)
          {
                  if (iter1 == NULL)
                  {
                          debug_("Iterator iter1 is NULL!!", "ok" );
                          break;
                  }
                  debug_("(*iter1).val", (*iter1).val);
          }
  }

  // Implodes the strings in the list-head
  // pointer explodeH and returns the mychar class
  void mychar::implode(char *glue)
  {
  }

  // Joins the strings in the list-head
  // pointer explodeH and returns the mychar class
  void mychar::join(char *glue)
  {
          implode(glue);
  }

  // Repeat the input string n times
  void mychar::repeat(char *input, unsigned int multiplier)
  {
          // For example -
          // repeat("1", 4) returns "1111"
          if (!input) // input == NULL
          {
                  val[0] = 0;
                  return;
          }

          val = (char *) my_malloc(strlen(input) * multiplier);
          for (unsigned int tmpii = 0; tmpii < multiplier; tmpii++)
          {
                  strcat(val, input);
          }
  }

  // Reverse the string
  void mychar::reverse()
  {
          // For example -
          //              reverse() on "12345" returns "54321"
          char aa;
          unsigned long tot_len = length();
          unsigned long midpoint = tot_len / 2;
          for (unsigned long tmpjj = 0; tmpjj < midpoint; tmpjj++)
          {
                  aa = val[tmpjj];  // temporary storage var
                  val[tmpjj] = val[tot_len - tmpjj - 1];  // swap the values
                  val[tot_len - tmpjj - 1] = aa; // swap the values
          }
  }

  // Replace all occurences of string 'needle' with 'str' in the haystack 'val'
  void mychar::replace(char *needle, char *str)
  {
          // For example -
          //              replace("AAA", "BB") on val = "some AAA and AAACC"
          //              reurns val = "some BB and BBCC"
  }

  // Translate certain chars
  void mychar::str_tr(char *from, char *to)
  {
          // For e.g ("abcd", "ABC") translates all occurences of each
          // character in 'from' to corresponding character in 'to'
  }

  // Center the text
  void center(int length, char padchar = ' ')
  {
          // For example -
          //              center(10, '*') on val="aa" returns "****aa****"
          //              center(10) on val="aa" returns "    aa    "
          // The result is a string of 'length' characters with val centered in it.
  }

  // Formats the original string by placing <number> of <padchar> characters
  // between each set of blank-delimited words. Leading and Trailing blanks
  // are always removed. If <number> is omitted or is 0, then all spaces are
  // in the string are removed. The default number is 0 and
  // default padchar ' '
  void space(int number, char padchar = ' ')
  {
          // For example -
          //              space(3) on val = "I do not know"
          //                              will return "I   do   not   know"
          //              space(1, '_') on val = "A deep black space"
          //                              will return "A_deep_black_space"
          //              space() on val = "I   know     this"
          //                              will return "Iknowthis"
  }

  // The result is string comprised of all characters between
  // and including <start> and <end>
  void xrange(char start, char end)
  {
          // For example -
          //      xrange('a', 'j') returns val = "abcdefghij"
          //      xrange(1, 8) returns val = "12345678"
  }

  // Removes any characters contained in <list>. The default character
  // for <list> is a blank ' '
  void compress(char *list)
  {
          // For example -
          //      compress("$,%") on val = "$1,934" returns "1934"
          //      compress() on val = "call me alavoor vasudevan" returns "callmealavoorvasudevan"
  }

  // Deletes a portion of string of <length> characters from <start> position.
  // If start is greater than the string length then string is unchanged.
  void delstr(int start, int length)
  {
          // For example -
          //      delstr(3,3) on val = 'pokemon' returns 'poon'
  }

  // The <newstr> in inserted into val beginning at <start>. The <newstr> will
  // be padded or truncated to <length> characters. The default <length> is
  // string length of newstr
  void insert(char *newstr, int start = 0, int length = 0, char padchar = ' ')
  {
          // For example -
          //      insert("something new", 4, 20, '*') on val = "old thing"
          //              returns "old something new*******thing"
  }

  // The result is string of <length> chars madeup of leftmost chars in val.
  // Quick way to left justify a string.
  void left(int length = 0, char padchar = ' ')
  {
          // For example -
          //      left(10) on val = "Wig" returns "Wig      "
          //      left(4) on val = "Wighat" returns "Wigh"
  }

  // The result is string of <length> chars madeup of rightmost chars in val.
  // Quick way to right justify a string.
  void right(int length = 0, char padchar = ' ')
  {
          // For example -
          //      right(10) on val = "never stop to saying" returns " to saying"
          //      right(4) on val = "Wighat" returns "ghat"
          //      right(6) on val = "4.50" returns "  4.50"
  }

  // The <newstr> in overlayed into val beginning at <start>. The <newstr> will
  // be padded or truncated to <length> characters. The default <length> is
  // string length of newstr
  void overlay(char *newstr, int start = 0, int length = 0, char padchar = ' ')
  {
          // For example -
          //      overlay("12345678", 4, 10, '*') on val = "oldthing is very bad"
          //              returns "old12345678**ery bad"
  }

  // sub string
  mychar mychar::substr(int start, int length = 0)
  {
          if (!length) // length == 0
                  return(mychar(& val[start-1]) );
          else
          {
                  mychar tmp = mychar(& val[start-1]);
                  tmp.val[length-1] = 0;
                  return(tmp);
          }
  }

  // If string is literrally equal to .. or not equal to
  // If type is false then it is ==
  bool mychar::equalto(const mychar & rhs, bool type = false)
  {
          if (type == false) // test for ==
          {
                  if (strlen(rhs.val) == length())
                  {
                          if (!strncmp(rhs.val, val, length())) //  == 0
                                  return true;
                          else
                                  return false;
                  }
                  else
                          return false;
          }
          else // test for !=
          {
                  if (strlen(rhs.val) != length())
                  {
                          if (!strncmp(rhs.val, val, length())) //  == 0
                                  return true;
                          else
                                  return false;
                  }
                  else
                          return false;
          }
  }

  // If string is literrally equal to .. or not equal to
  // If type is false then it is ==
  bool mychar::equalto(const char *rhs, bool type = false)
  {
          if (type == false) // test for ==
          {
                  if (strlen(rhs) == length())
                  {
                          if (!strncmp(rhs, val, length())) //  == 0
                                  return true;
                          else
                                  return false;
                  }
                  else
                          return false;
          }
          else // test for !=
          {
                  if (strlen(rhs) != length())
                  {
                          if (!strncmp(rhs, val, length())) //  == 0
                                  return true;
                          else
                                  return false;
                  }
                  else
                          return false;
          }
  }

  // find position, matching substr beginning from start..
  long mychar::pos(char *substr, unsigned long start)
  {
          char * tok;
          long res = -1;

          if ( !isnull() && (start < strlen(val) ) )
          {
                  tok = strstr(val + start, substr);
                  if (tok == NULL)
                          res = -1;
                  else
                          res = (long) (tok - val);
          }
          return res;
  }

  bool mychar::isnull()
  {
          if (val[0] == '\0')
                  return true;
          else
          {
                  if (val == NULL)
                          return true;
                  else
                          return false;
          }
  }

  void mychar::clear()
  {
          val = (char *) my_realloc(val, 10);
          val[0] = '\0';
  }

  // Remove trailing new-lines
  void mychar::chop()
  {
          unsigned long tmpii = strlen(val) - 1 ;
          for (; tmpii >= 0; tmpii--)
          {
                  if (val[tmpii] == '\n')
                          val[tmpii] = 0;
                  else
                          break;
          }
  }

  void mychar::ltrim()
  {
          // May cause problems in my_realloc since
          // location of bb will be destroyed !!
          char *bb = val;

          if (bb == NULL)
                  return;

          while (isspace(*bb))
                  bb++;
          debug_("bb", bb);

          if (bb != NULL && bb != val)
          {
                  debug_("doing string copy", "done");
                  //str_cpy(bb); // causes problems in my_realloc and bb is getting destroyed!!
                  strcpy(val, bb); // strcpy is ok since val space is > bb space
          }
          else
                  debug_("Not doing string copy", "done");
  }

  void mychar::rtrim()
  {
          for (long tmpii = strlen(val) - 1 ; tmpii >= 0; tmpii--)
          {
                  if ( isspace(val[tmpii]) )
                          val[tmpii] = '\0';
                  else
                          break;
          }
  }

  void mychar::trim()
  {
          rtrim();
          ltrim();
  }

  void mychar::to_lower()
  {
          for (long tmpii = strlen(val); tmpii >= 0; tmpii--)
          {
                  val[tmpii] = tolower(val[tmpii]);
          }
  }

  // Use for rounding off fractions digits of floats
  // Rounds-off floats with given precision and then
  // stores the result into mychar's val field
  // Also returns the result as a char *
  void mychar::roundf(float input_val, short precision)
  {
          float   integ_flt, deci_flt;
          const   short MAX_PREC = 4;

          debug_("In roundf", "ok");

          if (precision > MAX_PREC) // this is the max reliable precision
                  precision = MAX_PREC;

          // get the integral and decimal parts of the float value..
          deci_flt = modff(input_val, & integ_flt);

          for (int tmpzz = 0; tmpzz < precision; tmpzz++)
          {
                  debug_("deci_flt", deci_flt);
                  deci_flt *= 10;
          }
          debug_("deci_flt", deci_flt);

          unsigned long deci_int = (unsigned long) ( rint(deci_flt) );

          val = (char *) my_malloc(NUMBER_LENGTH); // float 70 digits max

          if (deci_int > 999) // (MAX_PREC) digits
                  sprintf(val, "%lu.%lu", (unsigned long) integ_flt, deci_int);
          else
          if (deci_int > 99) // (MAX_PREC - 1) digits
                  sprintf(val, "%lu.0%lu", (unsigned long) integ_flt, deci_int);
          else
          if (deci_int > 9) // (MAX_PREC - 2) digits
                  sprintf(val, "%lu.00%lu", (unsigned long) integ_flt, deci_int);
          else
                  sprintf(val, "%lu.00000%lu", (unsigned long) integ_flt, deci_int);
  }

  void mychar::roundd(double input_val, short precision)
  {
          double  integ_flt, deci_flt;
          const   short MAX_PREC = 6;

          if (precision > MAX_PREC) // this is the max reliable precision
                  precision = MAX_PREC;

          debug_("In roundd", "ok");
          // get the integral and decimal parts of the double value..
          deci_flt = modf(input_val, & integ_flt);

          for (int tmpzz = 0; tmpzz < precision; tmpzz++)
          {
                  debug_("deci_flt", deci_flt);
                  deci_flt *= 10;
          }
          debug_("deci_flt", deci_flt);

          val = (char *) my_malloc(NUMBER_LENGTH); // double 70 digits max

          unsigned long deci_int = (unsigned long) ( rint(deci_flt) );

          if (deci_int > 99999) // (MAX_PREC) digits
                  sprintf(val, "%lu.%lu", (unsigned long) integ_flt, deci_int);
          else
          if (deci_int > 9999) // (MAX_PREC - 1) digits
                  sprintf(val, "%lu.0%lu", (unsigned long) integ_flt, deci_int);
          else
          if (deci_int > 999) // (MAX_PREC - 2) digits
                  sprintf(val, "%lu.00%lu", (unsigned long) integ_flt, deci_int);
          else
          if (deci_int > 99) // (MAX_PREC - 3) digits
                  sprintf(val, "%lu.000%lu", (unsigned long) integ_flt, deci_int);
          else
          if (deci_int > 9) // (MAX_PREC - 4) digits
                  sprintf(val, "%lu.0000%lu", (unsigned long) integ_flt, deci_int);
          else // (MAX_PREC - 5) digits
                  sprintf(val, "%lu.00000%lu", (unsigned long) integ_flt, deci_int);
  }

  void mychar::to_upper()
  {
          for (long tmpii = strlen(val); tmpii >= 0; tmpii--)
          {
                  val[tmpii] = toupper(val[tmpii]);
          }
  }

  void mychar::str_cpy(char bb[])
  {
          debug_("In str_cpy bb", bb);
          if (bb == NULL)
          {
                  val[0] = '\0';
                  return;
          }

          unsigned long tmpii = strlen(bb);

          if (tmpii == 0)
          {
                  val[0] = '\0';
                  return;
          }

          debug_("In str_cpy tmpii", tmpii);
          debug_("In str_cpy val", val);
          val = (char *) my_realloc(val, tmpii);
          //val = new char [tmpii + SAFE_MEM_2];
          debug_("In str_cpy bb", bb);

          strncpy(val, bb, tmpii);
          debug_("In str_cpy val", val);
          val[tmpii] = '\0';
          debug_("In str_cpy val", val);
  }

  void mychar::str_cpy(int bb)
  {
          char tmpaa[100];
          sprintf(tmpaa, "%d", bb);
          str_cpy(tmpaa);
  }

  void mychar::str_cpy(unsigned long bb)
  {
          char tmpaa[100];
          sprintf(tmpaa, "%ld", bb);
          str_cpy(tmpaa);
  }

  void mychar::str_cpy(float bb)
  {
          char tmpaa[100];
          sprintf(tmpaa, "%f", bb);
          str_cpy(tmpaa);
  }

  void mychar::str_cat(char bb[])
  {
          unsigned long tmpjj = strlen(bb), tmpii = strlen(val);
          val = (char *) my_realloc(val, tmpii + tmpjj);
          debug_("val in str_cat() ", val);
          strncat(val, bb, tmpjj);
  }

  void mychar::str_cat(int bb)
  {
          char tmpaa[100];
          sprintf(tmpaa, "%d", bb);

          unsigned long tmpjj = strlen(tmpaa), tmpii = strlen(val);
          val = (char *) my_realloc(val, tmpii + tmpjj);
          strncat(val, tmpaa, tmpjj);
  }

  void mychar::str_cat(unsigned long bb)
  {
          char tmpaa[100];
          sprintf(tmpaa, "%ld", bb);

          unsigned long tmpjj = strlen(tmpaa), tmpii = strlen(val);
          val = (char *) my_realloc(val, tmpii + tmpjj);
          strncat(val, tmpaa, tmpjj);
  }

  void mychar::str_cat(float bb)
  {
          char tmpaa[100];
          sprintf(tmpaa, "%f", bb);

          unsigned long tmpjj = strlen(tmpaa), tmpii = strlen(val);
          val = (char *) my_realloc(val, tmpii + tmpjj);
          strncat(val, tmpaa, tmpjj);
  }

  mychar operator+ (const mychar & lhs, const mychar & rhs)
  {
          /*******************************************************/
          // Note : For adding two char strings, first cast mychar
          // as in -
          //aa = (mychar) "alkja " + " 99djd " ;
          /*******************************************************/

          mychar tmp(lhs);
          tmp.str_cat(rhs.val);
          return(tmp);

          /*
          if (mychar::global_mychar == NULL)
          {
                  mychar::global_mychar = new mychar;
                  mychar::global_mychar->str_cpy(lhs.val);
                  mychar::global_mychar->str_cat(rhs.val);
                  //return *mychar::global_mychar;
                  return mychar(mychar::global_mychar->val);
          }
          */
          /*
          else
          if (mychar::global_mychar1 == NULL)
          {
                  debug_("1)global", "ok" );
                  mychar::global_mychar1 = new mychar;
                  mychar::global_mychar1->str_cpy(lhs.val);
                  mychar::global_mychar1->str_cat(rhs.val);
                  return *mychar::global_mychar1;
          }
          */
          /*
          else
          {
                  fprintf(stderr, "\nError: cannot alloc global_mychar\n");
                  exit(-1);
          }
          */

          /*
          mychar *aa = new mychar;
          aa->str_cpy(lhs.val);
          aa->str_cat(rhs.val);
          return *aa;
          */
  }

  mychar mychar::operator+ (const mychar & rhs)
  {
          mychar tmp(*this);
          tmp.str_cat(rhs.val);
          debug_("rhs.val in operator+", rhs.val );
          debug_("tmp.val in operator+", tmp.val );
          return (tmp);
  }

  // Using reference will be faster in = operator
  mychar& mychar:: operator= ( const mychar& rhs )
  {
          if (& rhs == this)
          {
                  debug_("Fatal Error: In operator(=). rhs is == to 'this pointer'!!", "ok" );
                  return *this;
          }

          this->str_cpy(rhs.val);
          debug_("rhs value", rhs.val );

          // Free global vars memory
          //free_glob(& mychar::global_mychar);
          //if (mychar::global_mychar == NULL)
                  //fprintf(stderr, "\nglobal_mychar is freed!\n");

          //return (mychar(*this));
          return *this;
  }

  // Using reference will be faster in = operator
  mychar& mychar::operator+= (const mychar & rhs)
  {
          /*******************************************************/
          // Note : For adding two char strings, first cast mychar
          // as in -
          //aa += (mychar) "cccc" + "dddd";
          /*******************************************************/
          if (& rhs == this)
          {
                  debug_("Fatal error: In operator+= rhs is equals 'this' ptr", "ok");
                  return *this;
          }
          this->str_cat(rhs.val);
          return *this;
          //return (mychar(*this));
  }

  bool mychar::operator== (const mychar & rhs)
  {
          return(equalto(rhs.val));
  }

  bool mychar::operator== (const char *rhs)
  {
          return(equalto(rhs));
  }

  bool mychar::operator!= (const mychar & rhs)
  {
          return(equalto(rhs.val, true));
  }

  bool mychar::operator!= (const char *rhs)
  {
          return(equalto(rhs, true));
  }
  ______________________________________________________________________

  15.  ÷ºÎ D my_malloc.cpp

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  'Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.

  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  //Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************

  /*
  **      In your main() function put these lines -
                  char p_name[1024];
                  sprintf(p_name, "PROGRAM_NAME=%s", argv[0]);
                  putenv(p_name);
                  print_total_memsize(); // in the beginning
                  ......
                  ......
                  print_total_memsize(); // in the end
  */

  #include <stdio.h>
  #include <alloc.h>  // for c++ -- malloc, alloc etc...
  #include <stdlib.h>  // malloc, alloc..
  #include <time.h>  // strftime, localtime, ...
  #include <list.h>  // strftime, localtime, ...  see file include/g++/stl_list.h
  //#include <debug.h> // debug_("a", a);  debug2_("a", a, true);

  #include "my_malloc.h"

  const short SAFE_MEM = 10;
  const short DATE_MAX_SIZE = 200;

  const short MALLOC = 1;
  const short REALLOC     = 2;

  const short VOID_TYPE =         1;
  const short CHAR_TYPE =         2;
  const short SHORT_TYPE =        3;
  const short INT_TYPE =          4;
  const short LONG_TYPE =         5;
  const short FLOAT_TYPE =        6;
  const short DOUBLE_TYPE =       7;

  const char LOG_FILE[30] = "memory_error.log";

  // Uncomment this line to debug total mem size allocated...
  //#define DEBUG_MEM  "debug_memory_sizes_allocated"

  static void raise_error_exit(short mtype, short datatype, char fname[], int lineno);

  #ifdef DEBUG
  class MemCheck
  {
          public:
                  MemCheck(void *aptr, size_t amem_size, char fname[], int lineno);
                  void    *ptr;
                  size_t  mem_size;
                  static  list<MemCheck>          mcH;  // list head
                  static  unsigned long           total_memsize;  // total memory allocated
  };

  // Global variables ....
  list<MemCheck>          MemCheck::mcH;
  unsigned long           MemCheck::total_memsize = 0;

  MemCheck::MemCheck(void *aptr, size_t amem_size, char fname[], int lineno)
  {
          char func_name[100];
          FILE    *ferr = NULL;
          sprintf(func_name, "MemCheck() - File: %s Line: %d", fname, lineno);

          ferr = fopen(LOG_FILE, "a");
          if (ferr == NULL)
          {
                  fprintf(stdout, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  fprintf(stderr, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  #ifdef DEBUG_MEM
                          exit(-1);
                  #else
                          return;
                  #endif
          }

          // Search if the pointer already exists in the list...
          bool does_exist = false;
          list<MemCheck>::iterator iter1; // see file include/g++/stl_list.h
          //fprintf(ferr, "\n%s Before checking.. !!\n", func_name);
          if (MemCheck::mcH.empty() == true )
          {
                  //fprintf(ferr, "\n%s List is empty!!\n", func_name);
          }
          for (iter1 = MemCheck::mcH.begin(); iter1 != MemCheck::mcH.end(); iter1++)
          {
                  if (iter1 == NULL)
                  {
                          fprintf(ferr, "\n%s Iterator iter1 is NULL!!\n", func_name);
                          break;
                  }
                  if ( ((*iter1).ptr) == aptr)
                  {
                          does_exist = true;
                          fprintf(ferr, "\n%s Already exists!!\n", func_name);
                          fprintf(ferr, "\n%s Fatal Error exiting now ....!!\n", func_name);
                          #ifdef DEBUG_MEM
                                  exit(-1); //------------------------------------------------------------------>>>
                          #else
                                  return;
                          #endif
                          // Now change the mem size to new values...
                          // For total size - Remove old size and add new size
                          //fprintf(ferr, "\n%s total_memsize = %lu\n", func_name, (*iter1).total_memsize);
                          //fprintf(ferr, "\n%s mem_size = %u\n", func_name, (*iter1).mem_size);
                          //fprintf(ferr, "\n%s amem_size = %u\n", func_name, amem_size);
                          (*iter1).total_memsize = (*iter1).total_memsize + amem_size;
                          if ((*iter1).total_memsize > 0 )
                          {
                                  if ((*iter1).total_memsize >= (*iter1).mem_size )
                                          (*iter1).total_memsize = (*iter1).total_memsize - (*iter1).mem_size;
                                  else
                                  {
                                          fprintf(ferr, "\n\n%s total_memsize is less than mem_size!!", func_name);
                                          fprintf(ferr, "\n%s total_memsize = %lu", func_name, (*iter1).total_memsize);
                                          fprintf(ferr, "\n%s mem_size = %u", func_name, (*iter1).mem_size);
                                          fprintf(ferr, "\n%s amem_size = %u\n", func_name, amem_size);
                                  }
                          }
                          (*iter1).mem_size = amem_size;
                  }
          }

          // The pointer aptr does not exist in the list, so append it now...
          if (does_exist == false)
          {
                  //fprintf(ferr, "\n%s aptr Not found\n", func_name);
                  ptr = aptr;
                  mem_size = amem_size;
                  MemCheck::total_memsize += amem_size;
                  MemCheck::mcH.insert(MemCheck::mcH.end(), *this);
          }
          fclose(ferr);
  }

  static inline void call_check(void *aa, size_t tmpii, char fname[], int lineno)
  {
          MemCheck bb(aa, tmpii, fname, lineno);
          if (& bb);  // a dummy statement to avoid compiler warning msg.
  }

  static inline void remove_ptr(void *aa, char fname[], int lineno)
  {
          char    func_name[100];
          if (aa == NULL)
                  return;

          sprintf(func_name, "remove_ptr() - File: %s Line: %d", fname, lineno);
          FILE *ferr = NULL;
          ferr = fopen(LOG_FILE, "a");
          if (ferr == NULL)
          {
                  fprintf(stdout, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  fprintf(stderr, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  #ifdef DEBUG_MEM
                          exit(-1);
                  #else
                          return;
                  #endif
          }

          bool does_exist = false;
          if (MemCheck::mcH.empty() == true)
          {
                  //fprintf(ferr, "\n%s List is empty!!\n", func_name);
                  //fclose(ferr);
                  //return;
          }
          list<MemCheck>::iterator iter1; // see file include/g++/stl_list.h
          for (iter1 = MemCheck::mcH.begin(); iter1 != MemCheck::mcH.end(); iter1++)
          {
                  if (iter1 == NULL)
                  {
                          fprintf(ferr, "\n%s Iterator iter1 is NULL!!\n", func_name);
                          break;
                  }
                  if ( ((*iter1).ptr) == aa)
                  {
                          does_exist = true;
                          // Now change the mem size to new values...
                          // For total size - Remove old size
                          //fprintf(ferr, "\n%s total_memsize = %lu\n", func_name, (*iter1).total_memsize);
                          //fprintf(ferr, "\n%s mem_size = %u\n", func_name, (*iter1).mem_size);
                          if ((*iter1).total_memsize > 0 )
                          {
                                  if ((*iter1).total_memsize >= (*iter1).mem_size )
                                          (*iter1).total_memsize = (*iter1).total_memsize - (*iter1).mem_size;
                                  else
                                  {
                                          fprintf(ferr, "\n\n%s total_memsize is less than mem_size!!", func_name);
                                          fprintf(ferr, "\n%s total_memsize = %lu", func_name, (*iter1).total_memsize);
                                          fprintf(ferr, "\n%s mem_size = %u\n", func_name, (*iter1).mem_size);
                                  }
                          }
                          MemCheck::mcH.erase(iter1);
                          break;  // must break to avoid infinite looping
                  }
          }
          if (does_exist == false)
          {
                  //fprintf(ferr, "\n%s Fatal Error: - You did not allocate memory!! \n", func_name);
                  //fprintf(ferr, "\n%s The value passed is %s\n", func_name, (char *) aa);
          }
          else
                  //fprintf(ferr, "\n%s found\n", func_name);
          fclose(ferr);
  }

  static inline void call_free_check(void *aa, char *fname, int lineno)
  {
          char func_name[100];
          sprintf(func_name, "call_free_check() - File: %s Line: %d", fname, lineno);

          FILE *ferr = NULL;
          ferr = fopen(LOG_FILE, "a");
          if (ferr == NULL)
          {
                  fprintf(stdout, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  fprintf(stderr, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  #ifdef DEBUG_MEM
                          exit(-1);
                  #else
                          return;
                  #endif
          }

          bool does_exist = false;
          list<MemCheck>::iterator iter1; // see file include/g++/stl_list.h
          for (iter1 = MemCheck::mcH.begin(); iter1 != MemCheck::mcH.end(); iter1++)
          {
                  if (iter1 == NULL)
                  {
                          fprintf(ferr, "\n%s Iterator iter1 is NULL!!\n", func_name);
                          break;
                  }
                  if ( ((*iter1).ptr) == aa)
                  {
                          does_exist = true;
                          //fprintf(ferr, "\n%s iter1.mem_size = %u\n", func_name, (*iter1).mem_size);
                          //fprintf(ferr, "\n%s Total memory allocated = %lu\n",  func_name, (*iter1).total_memsize);
                          if ((*iter1).total_memsize > 0 )
                          {
                                  if ((*iter1).total_memsize >= (*iter1).mem_size )
                                          (*iter1).total_memsize = (*iter1).total_memsize - (*iter1).mem_size;
                                  else
                                  {
                                          fprintf(ferr, "\n\n%s total_memsize is less than mem_size!!", func_name);
                                          fprintf(ferr, "\n%s total_memsize = %lu", func_name, (*iter1).total_memsize);
                                          fprintf(ferr, "\n%s mem_size = %u", func_name, (*iter1).mem_size);
                                  }
                          }
                          MemCheck::mcH.erase(iter1);
                          break;  // must break to avoid infinite looping
                  }
          }
          if (does_exist == false)
          {
                  fprintf(ferr, "\n%s Fatal Error: free() - You did not allocate memory!!\n",
                                  func_name);
                  //fprintf(ferr, "\n%s The value passed is %s\n", func_name, (char *) aa);
                  fclose(ferr);
                  #ifdef DEBUG_MEM
                          exit(-1);
                  #else
                          return;
                  #endif
          }
          else
          {
                  //fprintf(ferr, "\n%s found\n", func_name);
          }
          fclose(ferr);
  }

  void local_print_total_memsize(char *fname, int lineno)
  {
          char func_name[100];
          sprintf(func_name, "local_print_total_memsize() - %s Line: %d", fname, lineno);

          FILE *ferr = NULL;
          ferr = fopen(LOG_FILE, "a");
          if (ferr == NULL)
          {
                  fprintf(stdout, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  fprintf(stderr, "\nWarning: Cannot open file %s\n", LOG_FILE);
                  #ifdef DEBUG_MEM
                          exit(-1);
                  #else
                          return;
                  #endif
          }

          fprintf(ferr, "\n%s Total memory MemCheck::total_memsize = %lu\n",  func_name, MemCheck::total_memsize);
          fclose(ferr);
  }
  #else  //------------> DEBUG

  void local_print_total_memsize(char *fname, int lineno)
  {
          // This function is available whether debug or no-debug...
  }

  #endif // DEBUG

  void local_my_free(void *aa, char fname[], int lineno)
  {
          if (aa == NULL)
                  return;
          call_free_check(aa, fname, lineno);
          free(aa);
          aa = NULL;
  }

  // size_t is type-defed unsigned long
  void *local_my_malloc(size_t size, char fname[], int lineno)
  {
          size_t  tmpii = size + SAFE_MEM;
          void *aa = NULL;
          aa = (void *) malloc(tmpii);
          if (aa == NULL)
                  raise_error_exit(MALLOC, VOID_TYPE, fname, lineno);
          memset(aa, 0, tmpii);
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }
  // size_t is type-defed unsigned long
  char *local_my_realloc(char *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpjj = 0;
          if (aa) // aa !=  NULL
                  tmpjj = strlen(aa);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (char) * (tmpqq);
          aa = (char *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);

          // do not memset!! memset(aa, 0, tmpii);
          aa[tmpqq-1] = 0;
          unsigned long kk = tmpjj;
          if (tmpjj > tmpqq)
                  kk = tmpqq;
          for ( ; kk < tmpqq; kk++)
                  aa[kk] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  // size_t is type-defed unsigned long
  short *local_my_realloc(short *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (short) * (tmpqq);
          aa = (short *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);
          // do not memset!! memset(aa, 0, tmpii);
          // Not for numbers!! aa[tmpqq-1] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  // size_t is type-defed unsigned long
  int *local_my_realloc(int *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (int) * (tmpqq);
          aa = (int *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);
          // do not memset!! memset(aa, 0, tmpii);
          // Not for numbers!! aa[tmpqq-1] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  // size_t is type-defed unsigned long
  long *local_my_realloc(long *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (long) * (tmpqq);
          aa = (long *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);
          // do not memset!! memset(aa, 0, tmpii);
          // Not for numbers!! aa[tmpqq-1] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  // size_t is type-defed unsigned long
  float *local_my_realloc(float *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (float) * (tmpqq);
          aa = (float *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);
          // do not memset!! memset(aa, 0, tmpii);
          // Not for numbers!! aa[tmpqq-1] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  // size_t is type-defed unsigned long
  double *local_my_realloc(double *aa, size_t size, char fname[], int lineno)
  {
          remove_ptr(aa, fname, lineno);
          unsigned long tmpqq = size + SAFE_MEM;
          size_t  tmpii = sizeof (double) * (tmpqq);
          aa = (double *) realloc(aa, tmpii);
          if (aa == NULL)
                  raise_error_exit(REALLOC, CHAR_TYPE, fname, lineno);
          // do not memset!! memset(aa, 0, tmpii);
          // Not for numbers!! aa[tmpqq-1] = 0;
          call_check(aa, tmpii, fname, lineno);
          return aa;
  }

  static void raise_error_exit(short mtype, short datatype, char fname[], int lineno)
  {
          if (mtype == MALLOC)
          {
                  fprintf(stdout, "\nFatal Error: malloc() failed!!");
                  fprintf(stderr, "\nFatal Error: malloc() failed!!");
          }
          else
          if (mtype == REALLOC)
          {
                  fprintf(stdout, "\nFatal Error: realloc() failed!!");
                  fprintf(stderr, "\nFatal Error: realloc() failed!!");
          }
          else
          {
                  fprintf(stdout, "\nFatal Error: mtype not supplied!!");
                  fprintf(stderr, "\nFatal Error: mtype not supplied!!");
                  exit(-1);
          }

          // Get current date-time and print time stamp in error file...
          char date_str[DATE_MAX_SIZE + SAFE_MEM];
          time_t tt;
          tt = time(NULL);
          struct tm *ct = NULL;
          ct = localtime(& tt); // time() in secs since Epoch 1 Jan 1970
          if (ct == NULL)
          {
                  fprintf(stdout, "\nWarning: Could not find the local time, localtime() failed\n");
                  fprintf(stderr, "\nWarning: Could not find the local time, localtime() failed\n");
          }
          else
                  strftime(date_str, DATE_MAX_SIZE , "%C", ct);
          FILE *ferr = NULL;
          char    filename[100];
          strcpy(filename, LOG_FILE);
          ferr = fopen(filename, "a");
          if (ferr == NULL)
          {
                  fprintf(stdout, "\nWarning: Cannot open file %s\n", filename);
                  fprintf(stderr, "\nWarning: Cannot open file %s\n", filename);
          }
          else
          {
                  // **************************************************
                  // ******* Do putenv in the main() function *********
                  //              char p_name[1024];
                  //              sprintf(p_name, "PROGRAM_NAME=%s", argv[0]);
                  //              putenv(p_name);
                  // **************************************************
                  char    program_name[200+SAFE_MEM];
                  if (getenv("PROGRAM_NAME") == NULL)
                  {
                          fprintf(ferr, "\n%sWarning: You did not putenv() PROGRAM_NAME env variable in main() function\n",
                                          date_str);
                          program_name[0] = 0;
                  }
                  else
                          strncpy(program_name, getenv("PROGRAM_NAME"), 200);

                  if (mtype == MALLOC)
                          fprintf(ferr, "\n%s: %s - Fatal Error - my_malloc() failed.", date_str, program_name);
                  else
                  if (mtype == REALLOC)
                  {
                          fprintf(ferr, "\n%s: %s - Fatal Error - my_realloc() failed.", date_str, program_name);
                          char dtype[50];
                          switch(datatype)
                          {
                                  case VOID_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  case CHAR_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  case SHORT_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  case INT_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  case LONG_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  case FLOAT_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  case DOUBLE_TYPE:
                                          strcpy(dtype, "char*");
                                          break;
                                  default:
                                          strcpy(dtype, "none*");
                                          break;
                          }
                          fprintf(ferr, "\n%s %s - Fatal Error: %s realloc() failed!!", date_str, program_name, dtype);
                  }

                  fprintf(ferr, "\n%s %s - Very severe error condition. Exiting application now....",
                                          date_str, program_name);
                  fclose(ferr);
          }

          exit(-1);
  }
  ______________________________________________________________________

  16.  ÷ºÎ E my_malloc.h

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  'Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.

  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  //Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************

  /*
  **      In your main() function put -
                  char p_name[1024];
                  sprintf(p_name, "PROGRAM_NAME=%s", argv[0]);
                  putenv(p_name);
                  print_total_memsize(); // in the beginning
                  ......
                  ......
                  print_total_memsize(); // in the end
  */

  /* Use zap instead of delete as this will be very clean!!
  ** Use do while to make it robust and bullet-proof macro
  */
  #define zap(x) do { if (x) { delete(x); x = 0; } } while (0)

  void *local_my_malloc(size_t size, char fname[], int lineno);

  char *local_my_realloc(char *aa, size_t size, char fname[], int lineno);
  short *local_my_realloc(short *aa, size_t size, char fname[], int lineno);
  void local_my_free(void *aa, char fname[], int lineno);

  void local_print_total_memsize(char fname[], int lineno);

  #define my_free(NM) (void) (local_my_free(NM, __FILE__, __LINE__))
  #define my_malloc(SZ) (local_my_malloc(SZ, __FILE__, __LINE__))
  #define my_realloc(NM, SZ) (local_my_realloc(NM, SZ, __FILE__, __LINE__))
  #define print_total_memsize() (void) (local_print_total_memsize(__FILE__, __LINE__))

  #ifdef DEBUG  //------------> DEBUG
  #else  //------------> DEBUG
  #define call_check(AA, BB, CC, DD) ((void) 0)
  #define call_free_check(AA, BB, CC) ((void) 0)
  #define remove_ptr(AA, CC, DD) ((void) 0)
  #endif //------------> DEBUG
  ______________________________________________________________________

  17.  ÷ºÎ F debug.h

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  'Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.
  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  //Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************

  #define print_log(AA, BB, CC, DD, EE) ((void) 0)

  #ifdef DEBUG

  #include <iostream>
  #include <string>
  //#include <assert.h>  // assert() macro which is also used for debugging

  const bool LOG_YES = true;  // print output to log file
  const bool LOG_NO = false;  // Do not print output to log file

  // Debugging code
  // Use debug2_ to output result to a log file

  #define debug_(NM, VL) (void) ( local_dbg(NM, VL, __FILE__, __LINE__) )
  #define debug2_(NM, VL, LOG_FILE) (void) ( local_dbg(NM, VL, __FILE__, __LINE__, LOG_FILE) )

  void local_dbg(char name[], char value[], char fname[], int lineno, bool logfile= false);
  void local_dbg(char name[], string value, char fname[], int lineno, bool logfile= false);
  void local_dbg(char name[], int value, char fname[], int lineno, bool logfile= false);
  void local_dbg(char name[], unsigned long value, char fname[], int lineno, bool logfile= false);
  void local_dbg(char name[], float value, char fname[], int lineno, bool logfile= false);
  void local_dbg(char name[], double value, char fname[], int lineno, bool logfile= false);

  #else  //--------> else

  #define debug_(NM, VL) ((void) 0)
  #define debug2_(NM, VL, LOG_FILE) ((void) 0)

  #endif // DEBUG
  ______________________________________________________________________

  18.  ÷ºÎ G debug.cpp

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  'Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.

  ______________________________________________________________________
  //*****************************************************************
  //ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  //Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  //ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  //*****************************************************************

  #ifdef DEBUG  // ONLY if DEBUG is defined then these functions below are needed

  #include "debug.h"
  //#include "log.h"

  // Variable value[] can be char, string, int, unsigned long, float, etc...

  void local_dbg(char name[], char value[], char fname[], int lineno, bool logfile) {
          if (value == NULL)
                  return;
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %s\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], string value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %s\n", fname, lineno, name, value.c_str());
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value.c_str() << endl; }

  void local_dbg(char name[], int value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %d\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], unsigned int value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %u\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], long value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %d\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], unsigned long value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %u\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], short value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %d\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], unsigned short value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %u\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], float value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %f\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  void local_dbg(char name[], double value, char fname[], int lineno, bool logfile) {
          if (logfile == true)
                  print_log("\nDebug %s : Line: %d %s is = %f\n", fname, lineno, name, value);
          else
                  cout << "\nDebug " << fname << ": Line: " << lineno << " " << name << " is = " << value << endl; }

  // You add many more here - value can be a class, ENUM, datetime, etc...

  #endif // DEBUG
  ______________________________________________________________________

  19.  ÷ºÎ H Makefile

  Download mychar ¿¡¼­ ¸ðµç ÇÁ·Î±×·¥µéÀ» ÇϳªÀÇ tar.gz È­ÀÏ·Î
  ´Ù¿î·Îµå¹ÞÀ» ¼ö ÀÖ´Ù. ÀÌ È­ÀÏÀ» ¹ÞÀ¸·Á¸é À¥ºê¶ó¿ìÀú¿¡¼­ ÀÌ È­ÀÏÀ»
  'Text' ŸÀÔÀ¸·Î ÀúÀåÇÑ´Ù.

  ______________________________________________________________________
  #//*****************************************************************
  #//ÀúÀÛ±ÇÀº GNU/GPL ¿¡ ÀÖÁö¸¸ ÀúÀÚÀÇ À̸§°ú À̸ÞÀÏÀº ¸ðµç º¹»çº»¿¡
  #//Æ÷ÇÔ½ÃÄÑ¾ß ÇÑ´Ù.
  #//ÀúÀÚ: Al Dev  À̸ÞÀÏ: alavoor@yahoo.com
  #//*****************************************************************

  .SUFFIXES: .pc .cpp .c .o

  CC=gcc
  CXX=g++

  MAKEMAKE=mm
  LIBRARY=libmychar.a
  DEST=/home/myname/lib

  # To build the library, and main test program  uncomment line below :-
  #MYCFLAGS=-O -Wall

  # To test without debug trace uncomment line below:-
  #MYCFLAGS=-g3 -Wall

  # To enable 'full debug ' tracing uncomment line below:-
  MYCFLAGS=-g3 -DDEBUG -Wall

  #PURIFY=purify -best-effort

  SRCS=my_malloc.cpp mychar.cpp debug.cpp example_mychar.cpp
  HDR=my_malloc.h  mychar.h debug.h
  OBJS=my_malloc.o mychar.o debug.o example_mychar.o
  EXE=mychar

  # For generating makefile dependencies..
  SHELL=/bin/sh

  CPPFLAGS=$(MYCFLAGS) $(OS_DEFINES)
  CFLAGS=$(MYCFLAGS) $(OS_DEFINES)

  #
  # If the libmychar.a is in the current
  # directory then use -L. (dash L dot)
  MYLIBDIR=-L$(MY_DIR)/libmy -L.

  ALLLDFLAGS= $(LDFLAGS)  $(MYLIBDIR)

  COMMONLIBS=-lstdc++ -lm
  MYLIBS=-lmychar
  LIBS=$(COMMONLIBS)  $(MYLIBS)

  all: $(LIBRARY) $(EXE)

  $(MAKEMAKE):
          @rm -f $(MAKEMAKE)
          $(PURIFY) $(CXX) -M  $(INCLUDE) $(CPPFLAGS) *.cpp > $(MAKEMAKE)

  $(EXE): $(OBJS)
          @echo "Creating a executable "
          $(PURIFY) $(CC) -o $(EXE) $(OBJS) $(ALLLDFLAGS) $(LIBS)

  $(LIBRARY): $(OBJS)
          @echo "\n***********************************************"
          @echo "   Loading $(LIBRARY) ... to $(DEST)"
          @echo "***********************************************"
          @ar cru $(LIBRARY) $(OBJS)
          @echo "\n "

  .cpp.o: $(SRCS) $(HDR)
  #       @echo "Creating a object files from " $*.cpp " files "
          $(PURIFY) $(CXX) -c  $(INCLUDE) $(CPPFLAGS) $*.cpp

  .c.o: $(SRCS) $(HDR)
  #       @echo "Creating a object files from " $*.c " files "
          $(PURIFY) $(CC) -c $(INCLUDE) $(CFLAGS) $*.c

  clean:
          rm -f *.o *.log *~ *.log.old *.pid core err a.out lib*.a afiedt.buf
          rm -f $(EXE)
          rm -f $(MAKEMAKE)

  #%.d: %.c
  #       @echo "Generating the dependency file *.d from *.c"
  #       $(SHELL) -ec '$(CC) -M $(CPPFLAGS) $< | sed '\''s/$*.o/& $@/g'\'' > $@'
  #%.d: %.cpp
  #       @echo "Generating the dependency file *.d from *.cpp"
  #       $(SHELL) -ec '$(CC) -M $(CPPFLAGS) $< | sed '\''s/$*.o/& $@/g'\'' > $@'

  # Must include all the c flags for -M option
  #$(MAKEMAKE):
  #       @echo "Generating the dependency file *.d from *.cpp"
  #       $(CXX) -M  $(INCLUDE) $(CPPFLAGS) *.cpp > $(MAKEMAKE)

  include $(MAKEMAKE)
  #include $(SRCS:.cpp=.d)
  #include $(SRCS:.c=.d)
  ______________________________________________________________________