Commit 652b6021 by Maarten L. Hekkelman

improved parser. is_non_quoted string

parent 7fe9c87b
......@@ -25,7 +25,7 @@
cmake_minimum_required(VERSION 3.16)
# set the project name
project(cifpp VERSION 5.0.5 LANGUAGES CXX)
project(cifpp VERSION 5.0.6 LANGUAGES CXX)
list(PREPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake")
......
Version 5.0.6
- Fix file::contains, using iequals
Version 5.0.5
- Fix code to work on 32 bit machines
......
......@@ -27,6 +27,7 @@
#pragma once
#include <map>
#include <regex>
#include <cif++/row.hpp>
......@@ -93,8 +94,6 @@ class sac_parser
static bool is_unquoted_string(std::string_view text)
{
auto s = text.begin();
bool result = true;
for (auto ch : text)
{
......@@ -104,14 +103,10 @@ class sac_parser
break;
}
// but be careful it does not contain e.g. stop_
if (result)
{
static const std::regex reservedRx(R"((^(?:data|save)|.*(?:loop|stop|global))_.+)", std::regex_constants::icase);
result = not std::regex_match(text.begin(), text.end(), reservedRx);
}
static const std::regex kReservedRx(R"(loop_|stop_|global_|data_\S+|save_\S+)", std::regex_constants::icase);
return result;
// but be careful it does not contain e.g. stop_
return result and not std::regex_match(text.begin(), text.end(), kReservedRx);
}
protected:
......
......@@ -125,7 +125,7 @@ void file::load_dictionary(std::string_view name)
bool file::contains(std::string_view name) const
{
return std::find_if(begin(), end(), [name](const datablock &db) { return db.name() == name; }) != end();
return std::find_if(begin(), end(), [name](const datablock &db) { return iequals(db.name(), name); }) != end();
}
datablock &file::operator[](std::string_view name)
......
......@@ -380,18 +380,13 @@ sac_parser::CIFToken sac_parser::get_next_token()
{
std::string s = to_lower_copy(m_token_value);
if (s == "global_")
result = CIFToken::GLOBAL;
else if (s == "stop_")
result = CIFToken::STOP;
else if (s == "loop_")
result = CIFToken::LOOP;
else if (s == "data_")
if (s == "data_")
{
state = State::DATA;
continue;
}
else if (s == "save_")
if (s == "save_")
{
state = State::SAVE;
continue;
......@@ -405,6 +400,12 @@ sac_parser::CIFToken sac_parser::get_next_token()
if (m_token_value == ".")
mTokenType = CIFValue::Inapplicable;
else if (iequals(m_token_value, "global_"))
result = CIFToken::GLOBAL;
else if (iequals(m_token_value, "stop_"))
result = CIFToken::STOP;
else if (iequals(m_token_value, "loop_"))
result = CIFToken::LOOP;
else if (m_token_value == "?")
{
mTokenType = CIFValue::Unknown;
......@@ -786,6 +787,9 @@ void sac_parser::parse_save_frame()
void parser::produce_datablock(const std::string &name)
{
if (VERBOSE >= 4)
std::cerr << "producing data_" << name << std::endl;
const auto &[iter, ignore] = m_file.emplace(name);
m_datablock = &(*iter);
}
......@@ -801,7 +805,7 @@ void parser::produce_category(const std::string &name)
void parser::produce_row()
{
if (VERBOSE >= 4)
if (VERBOSE >= 4 and m_category != nullptr)
std::cerr << "producing row for category " << m_category->name() << std::endl;
if (m_category == nullptr)
......
......@@ -2322,15 +2322,21 @@ _test.text ??
BOOST_AUTO_TEST_CASE(output_test_1)
{
cif::VERBOSE = 5;
auto data1 = R"(
data_Q
loop_
_test.text
"stop_the_crap"
stop_the_crap
'and stop_ this too'
'data_dinges'
'blablaglobal_bla'
blablaglobal_bla
boo.data_.whatever
'data_.whatever'
'stop_'
'loop_'
'global_'
)"_cf;
auto &db1 = data1.front();
......@@ -2341,11 +2347,15 @@ boo.data_.whatever
const char *s;
bool q;
} kS[] = {
{ "stop_the_crap", false },
{ "stop_the_crap", true },
{ "and stop_ this too", false },
{ "data_dinges", false },
{ "blablaglobal_bla", false },
{ "boo.data_.whatever", true }
{ "blablaglobal_bla", true },
{ "boo.data_.whatever", true },
{ "data_.whatever", false },
{ "stop_", false },
{ "loop_", false },
{ "global_", false }
};
BOOST_CHECK_EQUAL(test1.size(), sizeof(kS) / sizeof(T));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment