Skip to content

Instantly share code, notes, and snippets.

@trueroad
Last active February 10, 2020 13:29
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save trueroad/bdb81622c083ee544698c4bc55cda6a9 to your computer and use it in GitHub Desktop.
Save trueroad/bdb81622c083ee544698c4bc55cda6a9 to your computer and use it in GitHub Desktop.
Regex dispatcher table for C++11
;;; Directory Local Variables
;;; See Info node `(emacs) Directory Variables' for more information.
((c++-mode
(c-default-style . "gnu")
(indent-tabs-mode)))
all: sample
#
# Objects and libraries
#
OBJS = sample_main.o
LDLIBS =
#
# Flags
#
CXXFLAGS += -std=c++11
#
# Dependencies
#
DEPS = $(OBJS:.o=.d)
CPPFLAGS += -MMD -MP -MF $(@:.o=.d) -MT $@
-include $(DEPS)
#
# Rules
#
clean:
$(RM) *~ $(OBJS) $(DEPS)
.PHONY: all clean
sample: $(OBJS)
$(CXX) $(LDFLAGS) $(TARGET_ARCH) $^ $(LOADLIBES) $(LDLIBS) -o $@
//
// Regex dispatcher table for C++11
// https://gist.github.com/trueroad/bdb81622c083ee544698c4bc55cda6a9
//
// regex_dispatcher_f.hh: Regex dispatcher table class by std::function
//
// Copyright (C) 2018 Masamichi Hosoda.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
// OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
//
#ifndef INCLUDE_GUARD_REGEX_DISPATCHER_F_HH_
#define INCLUDE_GUARD_REGEX_DISPATCHER_F_HH_
#include <istream>
#include <regex>
#include <string>
#include <utility>
#include <vector>
namespace regex_dispatcher
{
class function_table
{
using callback_type = bool (const std::smatch &);
using table_type =
std::vector<std::pair<std::regex, std::function<callback_type>>>;
public:
function_table (table_type t):
table_ (t)
{
}
void process_line (const std::string &s)
{
std::smatch sm;
for (const auto &t: table_)
{
if (std::regex_match (s, sm, t.first))
{
if (t.second (sm))
break;
}
}
}
void process_stream (std::istream &is)
{
std::string line;
while (std::getline (is, line))
{
process_line (line);
}
}
private:
table_type table_;
};
}
#endif // INCLUDE_GUARD_REGEX_DISPATCHER_F_HH_
//
// Regex dispatcher table for C++11
// https://gist.github.com/trueroad/bdb81622c083ee544698c4bc55cda6a9
//
// regex_dispatcher_m.hh: Regex dispatcher table class by member function
//
// Copyright (C) 2018 Masamichi Hosoda.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
// OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
//
#ifndef INCLUDE_GUARD_REGEX_DISPATCHER_M_HH_
#define INCLUDE_GUARD_REGEX_DISPATCHER_M_HH_
#include <istream>
#include <regex>
#include <string>
#include <utility>
#include <vector>
namespace regex_dispatcher
{
template <class Derived>
class member_table
{
using callback_type = bool (Derived::*) (const std::smatch &);
using table_type =
std::vector<std::pair<std::regex, callback_type>>;
public:
member_table (table_type t):
table_ (t)
{
}
void process_line (const std::string &s)
{
std::smatch sm;
for (const auto &t: table_)
{
if (std::regex_match (s, sm, t.first))
{
if ((static_cast<Derived*> (this)->*(t.second)) (sm))
break;
}
}
}
void process_stream (std::istream &is)
{
std::string line;
while (std::getline (is, line))
{
process_line (line);
}
}
private:
table_type table_;
};
}
#endif // INCLUDE_GUARD_REGEX_DISPATCHER_M_HH_
//
// Regex dispatcher table for C++11
// https://gist.github.com/trueroad/bdb81622c083ee544698c4bc55cda6a9
//
// sample_bind.hh: Sample std::function table class by bind
//
// Copyright (C) 2018, 2020 Masamichi Hosoda.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
// OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
//
#ifndef INCLUDE_GUARD_SAMPLE_BIND_HH_
#define INCLUDE_GUARD_SAMPLE_BIND_HH_
#include <functional>
#include <iostream>
#include <regex>
#include <string>
#include "regex_dispatcher_f.hh"
class sample_bind: public regex_dispatcher::function_table
{
public:
sample_bind ():
regex_dispatcher::function_table
({
{std::regex (R"(^dec\t([\+\-]?\d+))"),
std::bind (&sample_bind::dec_handler, this,
std::placeholders::_1)},
{std::regex (R"(^fixed\t([\+\-]?\d+(\.?\d+)?))"),
std::bind (&sample_bind::fixed_handler, this,
std::placeholders::_1)},
{std::regex (R"(^scientific\t([\+\-]?\d+(\.?\d+)?([eE][\+\-]?\d+)?))"),
std::bind (&sample_bind::scientific_handler, this,
std::placeholders::_1)}
})
{
}
private:
bool dec_handler (const std::smatch &sm)
{
auto d {std::stoi (sm[1].str ())};
std::cout << "dec " << d << std::endl;
return true;
}
bool fixed_handler (const std::smatch &sm)
{
auto f {std::stod (sm[1].str ())};
std::cout << "fixed " << f << std::endl;
return true;
}
bool scientific_handler (const std::smatch &sm)
{
auto s {std::stod (sm[1].str ())};
std::cout << "sample " << s << std::endl;
return true;
}
};
#endif // INCLUDE_GUARD_SAMPLE_BIND_HH_
//
// Regex dispatcher table for C++11
// https://gist.github.com/trueroad/bdb81622c083ee544698c4bc55cda6a9
//
// sample_lambda.hh: Sample std::function table class by lambda
//
// Copyright (C) 2018 Masamichi Hosoda.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
// OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
//
#ifndef INCLUDE_GUARD_SAMPLE_LAMBDA_HH_
#define INCLUDE_GUARD_SAMPLE_LAMBDA_HH_
#include <iostream>
#include <regex>
#include <string>
#include "regex_dispatcher_f.hh"
class sample_lambda: public regex_dispatcher::function_table
{
public:
sample_lambda ():
regex_dispatcher::function_table
({
{std::regex (R"(^dec\t([\+\-]?\d+))"),
[this](const std::smatch &sm){return dec_handler (sm);}},
{std::regex (R"(^fixed\t([\+\-]?\d+(\.?\d+)?))"),
[this](const std::smatch &sm){return fixed_handler (sm);}},
{std::regex (R"(^scientific\t([\+\-]?\d+(\.?\d+)?([eE][\+\-]?\d+)?))"),
[this](const std::smatch &sm){return scientific_handler (sm);}}
})
{
}
private:
bool dec_handler (const std::smatch &sm)
{
auto d {std::stoi (sm[1].str ())};
std::cout << "dec " << d << std::endl;
return true;
}
bool fixed_handler (const std::smatch &sm)
{
auto f {std::stod (sm[1].str ())};
std::cout << "fixed " << f << std::endl;
return true;
}
bool scientific_handler (const std::smatch &sm)
{
auto s {std::stod (sm[1].str ())};
std::cout << "sample " << s << std::endl;
return true;
}
};
#endif // INCLUDE_GUARD_SAMPLE_LAMBDA_HH_
//
// Regex dispatcher table for C++11
// https://gist.github.com/trueroad/bdb81622c083ee544698c4bc55cda6a9
//
// main.cc: Sample main
//
// Copyright (C) 2018 Masamichi Hosoda.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
// OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
//
#include <exception>
#include <iostream>
#include <sstream>
#include "sample_bind.hh"
#include "sample_lambda.hh"
#include "sample_member.hh"
int main (void)
{
std::stringstream ss;
ss << "dec\t10\n"
<< "fixed\t1.234\n"
<< "scientific\t1.234e10\n";
std::cout << "--- std::function table by bind ---" << std::endl;
try
{
sample_bind sb;
sb.process_stream (ss);
}
catch (const std::exception &e)
{
std::cout << "exception: " << e.what () << std::endl;
}
ss.clear ();
ss.seekg (0, std::ios_base::beg);
std::cout << "--- std::function table by lambda ---" << std::endl;
try
{
sample_lambda sl;
sl.process_stream (ss);
}
catch (const std::exception &e)
{
std::cout << "exception: " << e.what () << std::endl;
}
ss.clear ();
ss.seekg (0, std::ios_base::beg);
std::cout << "--- member function table ---" << std::endl;
try
{
sample_member sm;
sm.process_stream (ss);
}
catch (const std::exception &e)
{
std::cout << "exception: " << e.what () << std::endl;
}
return 0;
}
//
// Regex dispatcher table for C++11
// https://gist.github.com/trueroad/bdb81622c083ee544698c4bc55cda6a9
//
// sample_member.hh: Sample member function table class
//
// Copyright (C) 2018, 2020 Masamichi Hosoda.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions
// are met:
//
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
// ARE DISCLAIMED.
// IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
// OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
// HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
// LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
// OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
//
#ifndef INCLUDE_GUARD_SAMPLE_MEMBER_HH_
#define INCLUDE_GUARD_SAMPLE_MEMBER_HH_
#include <iostream>
#include <regex>
#include <string>
#include "regex_dispatcher_m.hh"
class sample_member: public regex_dispatcher::member_table<sample_member>
{
public:
sample_member ():
regex_dispatcher::member_table<sample_member>
({
{std::regex (R"(^dec\t([\+\-]?\d+))"),
&sample_member::dec_handler},
{std::regex (R"(^fixed\t([\+\-]?\d+(\.?\d+)?))"),
&sample_member::fixed_handler},
{std::regex (R"(^scientific\t([\+\-]?\d+(\.?\d+)?([eE][\+\-]?\d+)?))"),
&sample_member::scientific_handler}
})
{
}
private:
bool dec_handler (const std::smatch &sm)
{
auto d {std::stoi (sm[1].str ())};
std::cout << "dec " << d << std::endl;
return true;
}
bool fixed_handler (const std::smatch &sm)
{
auto f {std::stod (sm[1].str ())};
std::cout << "fixed " << f << std::endl;
return true;
}
bool scientific_handler (const std::smatch &sm)
{
auto s {std::stod (sm[1].str ())};
std::cout << "sample " << s << std::endl;
return true;
}
};
#endif // INCLUDE_GUARD_SAMPLE_MEMBER_HH_
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment