출처 카페 > C++ Standard Te.. | 라온
원문 http://cafe.naver.com/cppstl/570

Singleton pattern을 이용하여 Config 파일을 이용하는 예 입니다.

Config는 여러 Application에서 사용할 수 있는 것이기 때문에 Singleton 형태로 한 번만 init하여

전체 공통으로 사용하도록 하고, 실제 프로그램 구성하여 사용 할 때는

System Environment(unix의 경우 getenv ) 설정으로 사용할 수 있습니다.

data container는 map을 이용하고 있으며, key, value 모두 string 입니다.

아래 예에서 사용한 Config.txt 내용은

#--------------------------------------------------------------------
# File Name : config.txt
# Author Name : Jeong il Ahn
# Description : Config file
# version : 1.0
# last edit : 200 . .
#---------------------------------------------------------------------
# Directory Information
#---------------------------------------------------------------------
DEFDIR=TESTDIR
#---------------------------------------------------------------------
# File Information
#---------------------------------------------------------------------
# End of File
EOF=[EOF]
# End of String
EOS=[EOS]
#---------------------------------------------------------------------

이런 형태이며, #은 주석으로 사용합니다.

key=value 형태로 구성되어 있습니다.

예제 main과 Config Source는 다음과 같습니다.

main.cpp

1 /*------------------------------------------------------------------------------------
2 * finename : main.cpp
3 * eng'r name : Jeong-il Ahn(raon_pgm@naver.com)
4 * date : 200 . 00. 00.
5 * title : This source is config for to test
6 *-----------------------------------------------------------------------------------*/
7
8 #include <iostream>
9 #include "config.h"
10
11 int main(int argc, char *argv[])
12 {
13 // config value initialize
14 if( !Config::instance()->init() ){
15 std::cerr << "System failed to initialize config!!!" << std::endl;
16 std::exit(EXIT_FAILURE);
17 }
18
19 std::cout << "End Of File is : ";
20 std::cout << Config::instance()->getCfgValue("EOF") << std::endl;
21
22 std::cout << "System Default Directory : ";
23 std::cout << Config::instance()->getCfgValue("DEFDIR") << std::endl;
24
25 }

config.h

1 #ifndef __CONFIG_H__
2 #define __CONFIG_H__
3
4 #include <map>
5 #include <string>
6 #include <fstream>
7
8 //! default config file declaration
9 static std::string DEFAULT_CONFIG = "config.txt";
10 //! configuration class
11 /*!
12 Programmer : Jeong-il Ahn(raon_pgm@naver.com) \n
13 date : 2001. 05. 14.\n
14 title : system config value define header\n
15 purpose : config value initialize from config.txt into map container\n
16 */
17 class Config{
18 public:
19 //! key/value container Map_STRSTR declaration. key : string, value : string
20 typedef std::map<std::string, std::string> Map_STRSTR;
21 //! config file load in mapConfigValue_
22 bool init();
23 //! singleton pattern - instance() function declaration
24 static Config* Config::instance();
25 //! mapConfigValue_에서 입력된 string으로 key 검색
26 /*!
27 \param key config내에서 찾고자 하는 key string
28 \return map container에서 key에 해당하는 value
29 */
30 std::string getCfgValue( std::string key )
31 {
32 return mapConfigValue_[key];
33 }
34
35 private:
36 //! static config point
37 static Config* the_config;
38 //! config file stream에서 memory로 데이터를 읽어 들인다.
39 /*!
40 \param *ifstr config file stream pointer
41 \return 파일 처리가 정상적으로 완료 되었을일 경우 true 이상이 있을 경우 false
42 */
43 bool readCfgIntoMemory ( std::ifstream &ifs );
44 //! map< string, string > type data container
45 Map_STRSTR mapConfigValue_;
46 };
47
48 #endif //!__CONFIG_H__

config.cpp

1 /*------------------------------------------------------------------------------------
2 * finename : config.cpp
3 * eng'r name : Jeong-il Ahn(raon_pgm@naver.com)
4 * date : 2001. 05. 14.
5 * title : system config value define source
6 * purpose : config value initialize from ./config/config.txt into map container
7 * description : using the singleton design pattern
8 *-----------------------------------------------------------------------------------*/
9
10 #include <iostream>
11 #include <fstream>
12 #include <cstdio>
13 #include <cstdlib>
14 #include <string>
15 #include <sys/types.h>
16
17 #include "config.h"
18
19 Config* Config::the_config = 0;
20
21 Config* Config::instance()
22 {
23 if( !the_config ){
24 the_config = new Config();
25 }
26 return the_config;
27 }
28
29 bool Config::init()
30 {
31 std::ifstream cfgFile( DEFAULT_CONFIG.c_str() );
32 if( ( !cfgFile ) || ( cfgFile.fail() ) ){
33 std::cerr << "Can't open file " << DEFAULT_CONFIG << std::endl;
34 return false;
35 }
36
37 if( !readCfgIntoMemory( cfgFile ) ) return false;
38
39 return true;
40 }
41
42 bool Config::readCfgIntoMemory( std::ifstream &ifs )
43 {
44 std::string oneLine;
45
46 while( !ifs.eof() ){
47 std::getline( ifs, oneLine );
48 if( oneLine == "" || oneLine[0] == '#' )
49 continue;
50 else{
51 size_t idx = oneLine.find( "=" );
52 if( idx == std::string::npos ){
53 std::cout << "Line = " << oneLine << std::endl;
54 std::cout << "Define failure line in config.txt" << std::endl;
55 continue;
56 }
57
58 std::string key, value;
59 key = value = oneLine;
60 key.erase( idx );
61 value.erase( 0, idx+1 );
62
63 mapConfigValue_[key] = value;
64 }
65 }
66 return true;
67 }