Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Compile time check if string contains quotes

I want to assert that an object JsonKey if constructed with a string that is known at compile time doesn't contain a quote. Here's what I have:

LiveDemo

#include<iostream>

template <size_t N>
constexpr bool check_no_quotes(const char (&str)[N])
{
    for (size_t i = 0; i < N; i++) // Initialize 'i' here
    {
        if (str[i] == '"')  // No need for the backslash here
            return false;
    }
    return true;
}

struct JsonKey
{
    template <size_t N>
    constexpr JsonKey(const char (&str)[N])
    {
        static_assert(check_no_quotes(str), "Can't have quotes");
    }
};

int main()
{
    // This will compile because it does not contain quotes
    JsonKey("json_key_without_quotes");

    // This will fail to compile because it contains quotes
    // JsonKey("json key with \"quotes\""); // Uncommenting this will trigger the static_assert error

    return 0;
}

The error I get:

<source>: In instantiation of 'constexpr JsonKey::JsonKey(const char (&)[N]) [with long unsigned int N = 24]':
<source>:26:38:   required from here
   26 |     JsonKey("json_key_without_quotes");
      |                                      ^
<source>:19:38: error: non-constant condition for static assertion
   19 |         static_assert(check_no_quotes(str), "Can't have quotes");
      |                       ~~~~~~~~~~~~~~~^~~~~
<source>:19:38:   in 'constexpr' expansion of 'check_no_quotes<24>((* & str))'
<source>:8:16: error: 'str' is not a constant expression
    8 |         if (str[i] == '"')  // No need for the backslash here
      |             ~~~^
Compiler returned: 1

I don't get why str is not compile-time available here.

like image 386
glades Avatar asked Nov 16 '25 06:11

glades


1 Answers

You can't static_assert on str because function arguments are not usable as constant expressions. See Can't use function parameter of a constexpr function in a constant expression for an explanation.

To achieve what you want, you can simply assert that the condition holds, and to ensure that it is a compile time check, make the constructor consteval.

struct JsonKey
{
    consteval JsonKey(std::string_view str)
    {
        assert(not std::ranges::contains(str, '"') && "Can't have quotes");
    }
};

demo.

Also, just use std::string_view as the parameter, and use a standard algorithm instead of writing it yourself.

like image 165
cigien Avatar answered Nov 18 '25 20:11

cigien



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!