diff options
author | Benoit Lormeau <blormeau@outlook.com> | 2020-09-27 12:20:08 +0200 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2020-09-27 21:15:25 +0200 |
commit | e4da2875c5c5aee3722e25749cc7904e5d108b3b (patch) | |
tree | b4bde93d2c3957334a68127ed043456e91bd394c | |
parent | eef794b8c645ea08fae3a9818c3a45ac5a4bccb4 (diff) | |
download | serenity-e4da2875c5c5aee3722e25749cc7904e5d108b3b.zip |
AK: Use templates instead of Function for Conditions in the GenericLexer
Since commit 1ec59f28cea56f1afced0994127e2df62300e618 turns the ctype macros
into functions we can now feed them directly to a GenericLexer! This will lead to
removing the ctype adapters that were kind-of excessive boilerplate, but needed as
the Kernel doesn't compile with the LibC.
-rw-r--r-- | AK/GenericLexer.cpp | 47 | ||||
-rw-r--r-- | AK/GenericLexer.h | 70 |
2 files changed, 61 insertions, 56 deletions
diff --git a/AK/GenericLexer.cpp b/AK/GenericLexer.cpp index cb116bb517..fe47fa6172 100644 --- a/AK/GenericLexer.cpp +++ b/AK/GenericLexer.cpp @@ -75,12 +75,6 @@ bool GenericLexer::next_is(const char* expected) const return true; } -// Tests the next character against a Condition -bool GenericLexer::next_is(Condition condition) const -{ - return condition(peek()); -} - // Consume a character and advance the parser index char GenericLexer::consume() { @@ -154,19 +148,6 @@ StringView GenericLexer::consume_line() return m_input.substring_view(start, length); } -// Consume and return characters while `condition` returns true -StringView GenericLexer::consume_while(Condition condition) -{ - size_t start = m_index; - while (!is_eof() && condition(peek())) - m_index++; - size_t length = m_index - start; - - if (length == 0) - return {}; - return m_input.substring_view(start, length); -} - // Consume and return characters until `stop` is peek'd // The `stop` character is ignored, as it is user-defined StringView GenericLexer::consume_until(char stop) @@ -199,19 +180,6 @@ StringView GenericLexer::consume_until(const char* stop) return m_input.substring_view(start, length); } -// Consume and return characters until `condition` return true -StringView GenericLexer::consume_until(Condition condition) -{ - size_t start = m_index; - while (!is_eof() && !condition(peek())) - m_index++; - size_t length = m_index - start; - - if (length == 0) - return {}; - return m_input.substring_view(start, length); -} - /* * Consume a string surrounded by single or double quotes. The returned * StringView does not include the quotes. An escape character can be provided @@ -276,13 +244,6 @@ void GenericLexer::ignore(size_t count) m_index += count; } -// Ignore characters while `condition` returns true -void GenericLexer::ignore_while(Condition condition) -{ - while (!is_eof() && condition(peek())) - m_index++; -} - // Ignore characters until `stop` is peek'd // The `stop` character is ignored as it is user-defined void GenericLexer::ignore_until(char stop) @@ -303,14 +264,6 @@ void GenericLexer::ignore_until(const char* stop) ignore(__builtin_strlen(stop)); } -// Ignore characters until `condition` return true -// We don't skip the stop character as it may not be a unique value -void GenericLexer::ignore_until(Condition condition) -{ - while (!is_eof() && !condition(peek())) - m_index++; -} - // CType adapters bool is_alpha(char c) { diff --git a/AK/GenericLexer.h b/AK/GenericLexer.h index 7800474ac4..ab1778c333 100644 --- a/AK/GenericLexer.h +++ b/AK/GenericLexer.h @@ -26,7 +26,6 @@ #pragma once -#include <AK/Function.h> #include <AK/String.h> #include <AK/StringView.h> @@ -37,9 +36,6 @@ public: explicit GenericLexer(const StringView& input); virtual ~GenericLexer(); - // A lambda/function can be used to match characters as the user pleases - using Condition = Function<bool(char)>; - size_t tell() const { return m_index; } size_t tell_remaining() const { return m_input.length() - m_index; } @@ -52,7 +48,6 @@ public: bool next_is(char) const; bool next_is(StringView) const; bool next_is(const char*) const; - bool next_is(Condition) const; char consume(); bool consume_specific(char); @@ -61,18 +56,75 @@ public: StringView consume(size_t count); StringView consume_all(); StringView consume_line(); - StringView consume_while(Condition); StringView consume_until(char); StringView consume_until(const char*); - StringView consume_until(Condition); StringView consume_quoted_string(char escape_char = 0); String consume_and_unescape_string(char escape_char = '\\'); void ignore(size_t count = 1); - void ignore_while(Condition); void ignore_until(char); void ignore_until(const char*); - void ignore_until(Condition); + + /* + * Conditions are used to match arbitrary characters. You can use lambdas, + * ctype functions, or is_any_of() and its derivatives (see below). + * A few examples: + * - `if (lexer.next_is(isdigit))` + * - `auto name = lexer.consume_while([](char c) { return isalnum(c) || c == '_'; });` + * - `lexer.ignore_until(is_any_of("<^>"));` + */ + + // Test the next character against a Condition + template<typename C> + bool next_is(C condition) const + { + return condition(peek()); + } + + // Consume and return characters while `condition` returns true + template<typename C> + StringView consume_while(C condition) + { + size_t start = m_index; + while (!is_eof() && condition(peek())) + m_index++; + size_t length = m_index - start; + + if (length == 0) + return {}; + return m_input.substring_view(start, length); + } + + // Consume and return characters until `condition` return true + template<typename C> + StringView consume_until(C condition) + { + size_t start = m_index; + while (!is_eof() && !condition(peek())) + m_index++; + size_t length = m_index - start; + + if (length == 0) + return {}; + return m_input.substring_view(start, length); + } + + // Ignore characters while `condition` returns true + template<typename C> + void ignore_while(C condition) + { + while (!is_eof() && condition(peek())) + m_index++; + } + + // Ignore characters until `condition` return true + // We don't skip the stop character as it may not be a unique value + template<typename C> + void ignore_until(C condition) + { + while (!is_eof() && !condition(peek())) + m_index++; + } protected: StringView m_input; |