summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Buland <eichlan@xagasoft.com>2010-10-27 03:27:05 +0000
committerMike Buland <eichlan@xagasoft.com>2010-10-27 03:27:05 +0000
commit10b68e6b5e7d12c7af51b960191e1be9eb788d2e (patch)
treeccc6375726b9acaf53b1bb67bec81747b0bde223
parent68b8b5136677435a84da7d277e78470ac4a41a64 (diff)
downloadlibbu++-10b68e6b5e7d12c7af51b960191e1be9eb788d2e.tar.gz
libbu++-10b68e6b5e7d12c7af51b960191e1be9eb788d2e.tar.bz2
libbu++-10b68e6b5e7d12c7af51b960191e1be9eb788d2e.tar.xz
libbu++-10b68e6b5e7d12c7af51b960191e1be9eb788d2e.zip
Interesting tweak to the variant and optparser classes. In the Variant, it
would always fail if a const char * was passed in, it now converts these silently to Bu::FStrings, good to know... Also, the OptParser now uses a Variant for overrides, meaning it doesn't have to do extra parsing, and the amount of code you have to write may be significantly reduced. Pretty sweet, overall. There is one downside. For the moment if you use a non-standard type or object as the target of a parameter it always needs to have a formatter >> operator defined, even if you override and the formatter >> operator is never called. Hopefully we can get around this in the future. Also, it looks like it should be relatively trivial to create conversion functions for the variant, they'll just be global template functions that take two parameters, source type and target type. Should be good times.
-rw-r--r--src/optparser.cpp36
-rw-r--r--src/optparser.h28
-rw-r--r--src/tools/myriad.cpp26
-rw-r--r--src/unitsuite.cpp2
-rw-r--r--src/variant.cpp6
-rw-r--r--src/variant.h1
6 files changed, 56 insertions, 43 deletions
diff --git a/src/optparser.cpp b/src/optparser.cpp
index 864d8ce..b81691d 100644
--- a/src/optparser.cpp
+++ b/src/optparser.cpp
@@ -45,7 +45,11 @@ void Bu::OptParser::parse( int argc, char **argv )
45 { 45 {
46 sOpt.set( argv[j]+2 ); 46 sOpt.set( argv[j]+2 );
47 } 47 }
48 try 48 if( !hlOption.has( sOpt ) )
49 {
50 optionError( "--" + sOpt );
51 }
52 else
49 { 53 {
50 // Long param, cool, that's easy, first search for = 54 // Long param, cool, that's easy, first search for =
51 Option *pOpt = hlOption.get( sOpt ); 55 Option *pOpt = hlOption.get( sOpt );
@@ -71,26 +75,28 @@ void Bu::OptParser::parse( int argc, char **argv )
71 } 75 }
72 else if( sExtraParam.isSet() ) 76 else if( sExtraParam.isSet() )
73 { 77 {
74 pOpt->pProxy->setValue( sExtraParam ); 78 pOpt->pProxy->setValueFromStr( sExtraParam );
75 } 79 }
76 else if( argv[j+1] != '\0' ) 80 else if( argv[j+1] != '\0' )
77 { 81 {
78 pOpt->pProxy->setValue( argv[j+1] ); 82 pOpt->pProxy->setValueFromStr( argv[j+1] );
79 j++; 83 j++;
80 } 84 }
81 } 85 }
82 } 86 }
83 catch( Bu::HashException &e )
84 {
85 optionError( "--" + sOpt );
86 }
87 } 87 }
88 else 88 else
89 { 89 {
90 int iCPos; 90 int iCPos;
91 for( iCPos = 1; argv[j][iCPos] != '\0'; iCPos++ ) 91 for( iCPos = 1; argv[j][iCPos] != '\0'; iCPos++ )
92 { 92 {
93 try 93 if( !hsOption.has( argv[j][iCPos] ) )
94 {
95 Bu::FString sOpt("-");
96 sOpt += argv[j][iCPos];
97 optionError( sOpt );
98 }
99 else
94 { 100 {
95 Option *pOpt = hsOption.get( argv[j][iCPos] ); 101 Option *pOpt = hsOption.get( argv[j][iCPos] );
96 char buf[2] = {argv[j][iCPos], '\0'}; 102 char buf[2] = {argv[j][iCPos], '\0'};
@@ -123,14 +129,14 @@ void Bu::OptParser::parse( int argc, char **argv )
123 } 129 }
124 else if( argv[j][iCPos+1] != '\0' ) 130 else if( argv[j][iCPos+1] != '\0' )
125 { 131 {
126 pOpt->pProxy->setValue( 132 pOpt->pProxy->setValueFromStr(
127 argv[j]+iCPos+1 133 argv[j]+iCPos+1
128 ); 134 );
129 break; 135 break;
130 } 136 }
131 else if( argv[j+1] ) 137 else if( argv[j+1] )
132 { 138 {
133 pOpt->pProxy->setValue( 139 pOpt->pProxy->setValueFromStr(
134 argv[j+1] 140 argv[j+1]
135 ); 141 );
136 j++; 142 j++;
@@ -138,12 +144,6 @@ void Bu::OptParser::parse( int argc, char **argv )
138 } 144 }
139 } 145 }
140 } 146 }
141 catch( Bu::HashException &e )
142 {
143 Bu::FString sOpt("-");
144 sOpt += argv[j][iCPos];
145 optionError( sOpt );
146 }
147 } 147 }
148 } 148 }
149 } 149 }
@@ -176,12 +176,12 @@ void Bu::OptParser::addOption( const Option &opt )
176 hlOption.insert( opt.sOpt, &lOption.last() ); 176 hlOption.insert( opt.sOpt, &lOption.last() );
177} 177}
178 178
179void Bu::OptParser::setOverride( char cOpt, const Bu::FString &sOverride ) 179void Bu::OptParser::setOverride( char cOpt, const Bu::Variant &sOverride )
180{ 180{
181 hsOption.get( cOpt )->sOverride = sOverride; 181 hsOption.get( cOpt )->sOverride = sOverride;
182} 182}
183 183
184void Bu::OptParser::setOverride( const Bu::FString &sOpt, const Bu::FString &sOverride ) 184void Bu::OptParser::setOverride( const Bu::FString &sOpt, const Bu::Variant &sOverride )
185{ 185{
186 hlOption.get( sOpt )->sOverride = sOverride; 186 hlOption.get( sOpt )->sOverride = sOverride;
187} 187}
diff --git a/src/optparser.h b/src/optparser.h
index 2936a4b..7ec69e5 100644
--- a/src/optparser.h
+++ b/src/optparser.h
@@ -15,6 +15,7 @@
15#include "bu/array.h" 15#include "bu/array.h"
16#include "bu/membuf.h" 16#include "bu/membuf.h"
17#include "bu/formatter.h" 17#include "bu/formatter.h"
18#include "bu/variant.h"
18 19
19namespace Bu 20namespace Bu
20{ 21{
@@ -40,7 +41,8 @@ namespace Bu
40 _ValueProxy(); 41 _ValueProxy();
41 virtual ~_ValueProxy(); 42 virtual ~_ValueProxy();
42 43
43 virtual void setValue( const Bu::FString & )=0; 44 virtual void setValueFromStr( const Bu::FString & )=0;
45 virtual void setValue( const Bu::Variant &vVar )=0;
44 virtual _ValueProxy *clone()=0; 46 virtual _ValueProxy *clone()=0;
45 }; 47 };
46 48
@@ -57,12 +59,28 @@ namespace Bu
57 { 59 {
58 } 60 }
59 61
60 virtual void setValue( const Bu::FString &sVal ) 62 virtual void setValueFromStr( const Bu::FString &sVal )
61 { 63 {
62 Bu::MemBuf mb( sVal ); 64 Bu::MemBuf mb( sVal );
63 Bu::Formatter f( mb ); 65 Bu::Formatter f( mb );
64 f >> v; 66 f >> v;
65 } 67 }
68
69 virtual void setValue( const Bu::Variant &vVar )
70 {
71 if( vVar.getType() == typeid(ptype) )
72 {
73 v = vVar.get<ptype>();
74 }
75 else if( vVar.getType() == typeid(Bu::FString) )
76 {
77 setValueFromStr( vVar.get<Bu::FString>() );
78 }
79 else
80 {
81 setValueFromStr( vVar.toString() );
82 }
83 }
66 84
67 virtual _ValueProxy *clone() 85 virtual _ValueProxy *clone()
68 { 86 {
@@ -87,7 +105,7 @@ namespace Bu
87 Bu::FString sHelp; 105 Bu::FString sHelp;
88 OptionSignal sUsed; 106 OptionSignal sUsed;
89 _ValueProxy *pProxy; 107 _ValueProxy *pProxy;
90 Bu::FString sOverride; 108 Bu::Variant sOverride;
91 Bu::FString sHelpDefault; 109 Bu::FString sHelpDefault;
92 }; 110 };
93 111
@@ -162,9 +180,9 @@ namespace Bu
162 addOption( sUsed, cOpt, "", sHelp ); 180 addOption( sUsed, cOpt, "", sHelp );
163 } 181 }
164 182
165 void setOverride( char cOpt, const Bu::FString &sOverride ); 183 void setOverride( char cOpt, const Bu::Variant &sOverride );
166 void setOverride( const Bu::FString &sOpt, 184 void setOverride( const Bu::FString &sOpt,
167 const Bu::FString &sOverride ); 185 const Bu::Variant &sOverride );
168 186
169 void setHelpDefault( const Bu::FString &sOpt, const Bu::FString &sTxt ); 187 void setHelpDefault( const Bu::FString &sOpt, const Bu::FString &sTxt );
170 188
diff --git a/src/tools/myriad.cpp b/src/tools/myriad.cpp
index 73ceba1..c6a3a4d 100644
--- a/src/tools/myriad.cpp
+++ b/src/tools/myriad.cpp
@@ -56,11 +56,11 @@ public:
56 addOption( iStream, 's', "stream", "Substream to work with."); 56 addOption( iStream, 's', "stream", "Substream to work with.");
57 addOption( sSrc, "src", "Source file for copying into a Myriad file."); 57 addOption( sSrc, "src", "Source file for copying into a Myriad file.");
58 58
59 setOverride( "create", "create" ); 59 setOverride( "create", modeCreate );
60 setOverride( "info", "info" ); 60 setOverride( "info", modeInfo );
61 setOverride( "new", "new" ); 61 setOverride( "new", modeStreamNew );
62 setOverride( "dump", "dump" ); 62 setOverride( "dump", modeStreamDump );
63 setOverride( "put", "put" ); 63 setOverride( "put", modeStreamPut );
64 64
65 parse( argc, argv ); 65 parse( argc, argv );
66 } 66 }
@@ -73,21 +73,9 @@ public:
73 Bu::FString sSrc; 73 Bu::FString sSrc;
74}; 74};
75 75
76Bu::Formatter &operator>>( Bu::Formatter &f, Mode &m ) 76Bu::Formatter &operator>>( Bu::Formatter &f, Mode &e )
77{ 77{
78 Bu::FString sTok = f.readToken(); 78 sio << "Uh oh, the formatter was called..." << sio.nl;
79 if( sTok == "create" )
80 m = modeCreate;
81 else if( sTok == "info" )
82 m = modeInfo;
83 else if( sTok == "new" )
84 m = modeStreamNew;
85 else if( sTok == "dump" )
86 m = modeStreamDump;
87 else if( sTok == "put" )
88 m = modeStreamPut;
89 else
90 m = modeNone;
91 return f; 79 return f;
92} 80}
93 81
diff --git a/src/unitsuite.cpp b/src/unitsuite.cpp
index 7a20128..ce6d037 100644
--- a/src/unitsuite.cpp
+++ b/src/unitsuite.cpp
@@ -40,7 +40,7 @@ int Bu::UnitSuite::run( int argc, char *argv[] )
40 p.addOption( Bu::slot( this, &Bu::UnitSuite::onListCases ), 'l', "list", 40 p.addOption( Bu::slot( this, &Bu::UnitSuite::onListCases ), 'l', "list",
41 "List available test cases." ); 41 "List available test cases." );
42 p.addOption( bCleanup, "no-cleanup", "Don't erase temp files."); 42 p.addOption( bCleanup, "no-cleanup", "Don't erase temp files.");
43 p.setOverride( "no-cleanup", "false" ); 43 p.setOverride( "no-cleanup", false );
44 p.addHelpOption(); 44 p.addHelpOption();
45 p.parse( argc, argv ); 45 p.parse( argc, argv );
46 46
diff --git a/src/variant.cpp b/src/variant.cpp
index a66ec39..a239e0f 100644
--- a/src/variant.cpp
+++ b/src/variant.cpp
@@ -34,6 +34,12 @@ Bu::Variant::Variant( const Variant &v ) :
34 } 34 }
35} 35}
36 36
37Bu::Variant::Variant( const char *t ) :
38 pCore( NULL )
39{
40 set( Bu::FString( t ) );
41}
42
37Bu::Variant::~Variant() 43Bu::Variant::~Variant()
38{ 44{
39 if( pCore ) 45 if( pCore )
diff --git a/src/variant.h b/src/variant.h
index 5482ee3..8e1203c 100644
--- a/src/variant.h
+++ b/src/variant.h
@@ -98,6 +98,7 @@ namespace Bu
98 public: 98 public:
99 Variant(); 99 Variant();
100 Variant( const Variant &v ); 100 Variant( const Variant &v );
101 Variant( const char *t );
101 template<class t> 102 template<class t>
102 Variant( const t &v ) : 103 Variant( const t &v ) :
103 pCore( new VariantType<t>() ) 104 pCore( new VariantType<t>() )