api2021 part I #4
|
@ -156,6 +156,39 @@ Space::Space(const Space * space)
|
|||
}
|
||||
|
||||
|
||||
void Space::clear()
|
||||
{
|
||||
set_null();
|
||||
}
|
||||
|
||||
|
||||
|
||||
void Space::set_null()
|
||||
{
|
||||
initialize_value_null_if_needed();
|
||||
}
|
||||
|
||||
void Space::set_empty_string()
|
||||
{
|
||||
initialize_value_string_if_needed();
|
||||
}
|
||||
|
||||
void Space::set_empty_wstring()
|
||||
{
|
||||
initialize_value_wstring_if_needed();
|
||||
}
|
||||
|
||||
void Space::set_empty_table()
|
||||
{
|
||||
initialize_value_table_if_needed();
|
||||
}
|
||||
|
||||
void Space::set_empty_object()
|
||||
{
|
||||
initialize_value_object_if_needed();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
void Space::set(bool val)
|
||||
|
@ -220,14 +253,28 @@ void Space::set(double val)
|
|||
|
||||
void Space::set(const char * str)
|
||||
{
|
||||
initialize_value_string_if_needed();
|
||||
value.value_string = str;
|
||||
if( str == nullptr )
|
||||
{
|
||||
initialize_value_null_if_needed();
|
||||
}
|
||||
else
|
||||
{
|
||||
initialize_value_string_if_needed();
|
||||
value.value_string = str;
|
||||
}
|
||||
}
|
||||
|
||||
void Space::set(const wchar_t * str)
|
||||
{
|
||||
initialize_value_wstring_if_needed();
|
||||
value.value_wstring = str;
|
||||
if( str == nullptr )
|
||||
{
|
||||
initialize_value_null_if_needed();
|
||||
}
|
||||
else
|
||||
{
|
||||
initialize_value_wstring_if_needed();
|
||||
value.value_wstring = str;
|
||||
}
|
||||
}
|
||||
|
||||
void Space::set(const std::string & str)
|
||||
|
|
166
space/space.h
166
space/space.h
|
@ -55,110 +55,72 @@ namespace PT
|
|||
|
||||
|
||||
/*
|
||||
A parser for parsing config files.
|
||||
|
||||
A config file can look like this:
|
||||
variable1 = value 1
|
||||
variable2 = " value 2 "
|
||||
variable3 = (value 1, value 2)
|
||||
variable4 = (" value 1 " , "value2", value 3)
|
||||
Simple form:
|
||||
key = value
|
||||
|
||||
sample of use:
|
||||
SpaceParser parser;
|
||||
parser.Parse("/path/to/config");
|
||||
If value is equal to 'null' then the internal representation is equal to Type::type_null, e.g:
|
||||
key = null
|
||||
|
||||
if( parser.status == SpaceParser::ok )
|
||||
{
|
||||
// the whole config we have in parser.table
|
||||
}
|
||||
If value is either 'false' or 'true' then the internal representation is Type::type_bool, e.g:
|
||||
key = false
|
||||
key = true
|
||||
|
||||
config syntax:
|
||||
option = list
|
||||
If value is an integer number and not an overflow has occured while parsing then type of the value
|
||||
is Type::type_long (type is 'long long' internally):
|
||||
key = 1000
|
||||
|
||||
list can consists of any number of items, if you're using more than one item you should
|
||||
use brackets ()
|
||||
If value is a floating point number then type is Type::type_double (type is 'double' internally):
|
||||
key = 123.45
|
||||
key = 123.45e+10
|
||||
|
||||
for one item the brackets can be ommited:
|
||||
option = value
|
||||
white characters at the beginning of the value (and at the end) will be trimmed,
|
||||
or you can use quotes:
|
||||
option = "value"
|
||||
option2 = "value with spaces at the end "
|
||||
In other cases value has Type::type_wstring type.
|
||||
|
||||
the form without quotes:
|
||||
option = value
|
||||
should be written in one line, so this is not allowed:
|
||||
option =
|
||||
value
|
||||
you can use a new line characters only between brackets and quotes:
|
||||
option = "this is
|
||||
a multiline string"
|
||||
option = ( value1,
|
||||
value2 )
|
||||
The form with quotation marks:
|
||||
key = "value"
|
||||
In such a case value has Type::type_wstring type and can be multiline e.g:
|
||||
key = "multiline
|
||||
value"
|
||||
In this form you can have spaces around value, e.g.:
|
||||
key = " value with spaces "
|
||||
|
||||
but there is one requirement: the first character " or ( should be in the same line,
|
||||
so this is not allowed
|
||||
option =
|
||||
"this is wrong"
|
||||
but this is ok:
|
||||
option = "
|
||||
that is ok"
|
||||
|
||||
empty lists:
|
||||
option = ()
|
||||
this creates an empty list: parser.table['option'].empty() == true
|
||||
The value can be a list:
|
||||
key = (value1,value2)
|
||||
or the same written with spaces around:
|
||||
key = ( value1 , value2 )
|
||||
or written in multiline fashion:
|
||||
key = (
|
||||
value1,
|
||||
value2,
|
||||
)
|
||||
a colon after value2 is optional.
|
||||
|
||||
option =
|
||||
this creates an empty list too (the same as previously)
|
||||
List can be written with quotation marks too:
|
||||
key = (
|
||||
"value1",
|
||||
"value2",
|
||||
"value3
|
||||
with a new line character inside",
|
||||
)
|
||||
|
||||
option = ""
|
||||
but this doesn't create an empty list, it creates a list with one (empty) item
|
||||
List without value:
|
||||
key = ()
|
||||
is equal to simple form without value, e.g.:
|
||||
key =
|
||||
|
||||
commentaries:
|
||||
# this is a commentary (until the end of the line)
|
||||
option = value # this is a commentary too
|
||||
|
||||
commentaries are treated as white characters, other example:
|
||||
option = ( # this is my list
|
||||
"value 1" # this is a value one
|
||||
value 2 # and this is a value two
|
||||
) # end of my list
|
||||
|
||||
overwriting:
|
||||
option1 = some value
|
||||
option1 = other value
|
||||
# always the last option is used so option1 is "other value"
|
||||
|
||||
list delimiter:
|
||||
option1 = (value1, value2, value3)
|
||||
option2 = ("value1", "value2", "value3")
|
||||
above we're using a comma ',' as a list delimiter but when using quotes (second line)
|
||||
the commas can be omitted:
|
||||
option2 = ("value1" "value2" "value3")
|
||||
Difference between a simple form and a list is when parsing the colon, in simple form the colon is a part of the value, e.g.:
|
||||
key = value with , a colon inside
|
||||
this is equal to:
|
||||
key = "value with , a colon inside"
|
||||
|
||||
white characters:
|
||||
the name of an option cannot consist of white characters
|
||||
some option = value # this is wrong
|
||||
some_option = value # this is ok
|
||||
and in a form of a list it would have two values:
|
||||
key = (value with , a colon inside)
|
||||
would be equal to:
|
||||
key = ("value with" , "a colon inside")
|
||||
|
||||
which characters are allowed in an option name is defined by IsVariableChar() method
|
||||
|
||||
you can use white characters in values
|
||||
option = value with spaces or tabs
|
||||
white characters at the beginning and at the end will be trimmed,
|
||||
so if you want them use quotes:
|
||||
option = " other value with spaces "
|
||||
|
||||
special characters in quoted strings:
|
||||
option = "this is a string with \" a quote inside"
|
||||
the option will be: this is a string with " a quote inside
|
||||
\\ - means one \
|
||||
basically: \char produces char
|
||||
so:
|
||||
"\a" gives "a"
|
||||
"\\" gives "\"
|
||||
"\Z" gives "Z" and so on
|
||||
you can call UseEscapeChar(false) to turn this off
|
||||
|
||||
|
||||
*/
|
||||
|
@ -242,7 +204,15 @@ public:
|
|||
Space(const Space * space);
|
||||
|
||||
|
||||
void clear();
|
||||
|
||||
// set a new value
|
||||
void set_null();
|
||||
void set_empty_string();
|
||||
void set_empty_wstring();
|
||||
void set_empty_table();
|
||||
void set_empty_object();
|
||||
|
||||
void set(bool val);
|
||||
void set(short val);
|
||||
void set(int val);
|
||||
|
@ -258,7 +228,7 @@ public:
|
|||
void set(const wchar_t * str);
|
||||
void set(const std::string & str);
|
||||
void set(const std::wstring & str);
|
||||
void set(const Space * space = nullptr);
|
||||
void set(const Space * space);
|
||||
|
||||
|
||||
// add a value to the table, change to table if needed, return the reference to the new inserted item
|
||||
|
@ -652,20 +622,28 @@ protected:
|
|||
template<typename StreamType>
|
||||
void serialize_json_float(StreamType & str) const
|
||||
{
|
||||
wchar_t buffer[50];
|
||||
wchar_t buffer[100];
|
||||
size_t buffer_len = sizeof(buffer) / sizeof(char);
|
||||
|
||||
std::swprintf(buffer, buffer_len, L"%f", value.value_float);
|
||||
int chars_written = std::swprintf(buffer, buffer_len, L"%e", static_cast<double>(value.value_float));
|
||||
|
||||
if( errno == EOVERFLOW || chars_written < 0 )
|
||||
buffer[0] = 0;
|
||||
|
||||
serialize_string_buffer(buffer, str, Escape::escape_json);
|
||||
}
|
||||
|
||||
template<typename StreamType>
|
||||
void serialize_json_double(StreamType & str) const
|
||||
{
|
||||
wchar_t buffer[50];
|
||||
size_t buffer_len = sizeof(buffer) / sizeof(char);
|
||||
wchar_t buffer[100];
|
||||
size_t buffer_len = sizeof(buffer) / sizeof(wchar_t);
|
||||
|
||||
int chars_written = std::swprintf(buffer, buffer_len, L"%e", value.value_double);
|
||||
|
||||
if( errno == EOVERFLOW || chars_written < 0 )
|
||||
buffer[0] = 0;
|
||||
|
||||
std::swprintf(buffer, buffer_len, L"%f", value.value_double);
|
||||
serialize_string_buffer(buffer, str, Escape::escape_json);
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue