Warning: ISO C++ forbids converting a string constant to ‘char*’ for a static `constexpr char*` data...












17















Why does this code return a warning




warning: ISO C++ forbids converting a string constant to ‘char*’
[-Wwrite-strings]




if




A constexpr specifier used in an object declaration or non-static
member function (until C++14) implies const. A constexpr specifier used in a function or static member variable (since C++17) declaration implies inline.




(cppreference.com)



#include <cassert>    
#include <string>
#include <iostream>

struct A
{
// warning: ISO C++ forbids converting a string constant to ‘char*’
static constexpr char* name_ = "A";
static constexpr char* name() { return name_; };
};

int main()
{};


If I add a const after constexpr, the warning is gone:



#include <cassert>    
#include <string>
#include <iostream>



struct A
{
static constexpr const char* name_ = "A";
static constexpr const char* name() { return name_; };
};

int main()
{};


With g++ --version = g++ (GCC) 8.2.1 20181127,



compilation g++ -O3 -std=c++2a -Wall main.cpp -o main.



Does the constexpr not imply const on static data members?










share|improve this question

























  • stackoverflow.com/questions/28845058/…

    – Mat
    11 hours ago











  • stackoverflow.com/questions/14116003/…

    – Brandon Lyons
    11 hours ago
















17















Why does this code return a warning




warning: ISO C++ forbids converting a string constant to ‘char*’
[-Wwrite-strings]




if




A constexpr specifier used in an object declaration or non-static
member function (until C++14) implies const. A constexpr specifier used in a function or static member variable (since C++17) declaration implies inline.




(cppreference.com)



#include <cassert>    
#include <string>
#include <iostream>

struct A
{
// warning: ISO C++ forbids converting a string constant to ‘char*’
static constexpr char* name_ = "A";
static constexpr char* name() { return name_; };
};

int main()
{};


If I add a const after constexpr, the warning is gone:



#include <cassert>    
#include <string>
#include <iostream>



struct A
{
static constexpr const char* name_ = "A";
static constexpr const char* name() { return name_; };
};

int main()
{};


With g++ --version = g++ (GCC) 8.2.1 20181127,



compilation g++ -O3 -std=c++2a -Wall main.cpp -o main.



Does the constexpr not imply const on static data members?










share|improve this question

























  • stackoverflow.com/questions/28845058/…

    – Mat
    11 hours ago











  • stackoverflow.com/questions/14116003/…

    – Brandon Lyons
    11 hours ago














17












17








17








Why does this code return a warning




warning: ISO C++ forbids converting a string constant to ‘char*’
[-Wwrite-strings]




if




A constexpr specifier used in an object declaration or non-static
member function (until C++14) implies const. A constexpr specifier used in a function or static member variable (since C++17) declaration implies inline.




(cppreference.com)



#include <cassert>    
#include <string>
#include <iostream>

struct A
{
// warning: ISO C++ forbids converting a string constant to ‘char*’
static constexpr char* name_ = "A";
static constexpr char* name() { return name_; };
};

int main()
{};


If I add a const after constexpr, the warning is gone:



#include <cassert>    
#include <string>
#include <iostream>



struct A
{
static constexpr const char* name_ = "A";
static constexpr const char* name() { return name_; };
};

int main()
{};


With g++ --version = g++ (GCC) 8.2.1 20181127,



compilation g++ -O3 -std=c++2a -Wall main.cpp -o main.



Does the constexpr not imply const on static data members?










share|improve this question
















Why does this code return a warning




warning: ISO C++ forbids converting a string constant to ‘char*’
[-Wwrite-strings]




if




A constexpr specifier used in an object declaration or non-static
member function (until C++14) implies const. A constexpr specifier used in a function or static member variable (since C++17) declaration implies inline.




(cppreference.com)



#include <cassert>    
#include <string>
#include <iostream>

struct A
{
// warning: ISO C++ forbids converting a string constant to ‘char*’
static constexpr char* name_ = "A";
static constexpr char* name() { return name_; };
};

int main()
{};


If I add a const after constexpr, the warning is gone:



#include <cassert>    
#include <string>
#include <iostream>



struct A
{
static constexpr const char* name_ = "A";
static constexpr const char* name() { return name_; };
};

int main()
{};


With g++ --version = g++ (GCC) 8.2.1 20181127,



compilation g++ -O3 -std=c++2a -Wall main.cpp -o main.



Does the constexpr not imply const on static data members?







c++ c++11 static constexpr






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited 11 hours ago







tmaric

















asked 11 hours ago









tmarictmaric

2,6551949




2,6551949













  • stackoverflow.com/questions/28845058/…

    – Mat
    11 hours ago











  • stackoverflow.com/questions/14116003/…

    – Brandon Lyons
    11 hours ago



















  • stackoverflow.com/questions/28845058/…

    – Mat
    11 hours ago











  • stackoverflow.com/questions/14116003/…

    – Brandon Lyons
    11 hours ago

















stackoverflow.com/questions/28845058/…

– Mat
11 hours ago





stackoverflow.com/questions/28845058/…

– Mat
11 hours ago













stackoverflow.com/questions/14116003/…

– Brandon Lyons
11 hours ago





stackoverflow.com/questions/14116003/…

– Brandon Lyons
11 hours ago












2 Answers
2






active

oldest

votes


















35














constexpr does imply const, but in this case it applies const to the "wrong thing".



constexpr char*


is basically the same as



char * const


which is a constant pointer to a non-const char. This won't work because string literals have the type const char[N] so it would cast away the constness of the array elements.



constexpr const char*


on the other hand, is basically the same as



char const * const


which is a constant pointer to a constant char, which is what you want as it preserves the constness of the elements.






share|improve this answer

































    10














    There is a usual difference between a constant pointer and a pointer to constant. By making your constexpr char* you made a pointer itself a constexpr (and, of course, const), but it still attempts to point at non-const character - and this is wrong, as string literals are const. Solution:



    constexpr const char* ch = "StackOverflow!";


    Which declares a constexpr pointer to const.






    share|improve this answer



















    • 1





      I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

      – Eljay
      11 hours ago











    Your Answer






    StackExchange.ifUsing("editor", function () {
    StackExchange.using("externalEditor", function () {
    StackExchange.using("snippets", function () {
    StackExchange.snippets.init();
    });
    });
    }, "code-snippets");

    StackExchange.ready(function() {
    var channelOptions = {
    tags: "".split(" "),
    id: "1"
    };
    initTagRenderer("".split(" "), "".split(" "), channelOptions);

    StackExchange.using("externalEditor", function() {
    // Have to fire editor after snippets, if snippets enabled
    if (StackExchange.settings.snippets.snippetsEnabled) {
    StackExchange.using("snippets", function() {
    createEditor();
    });
    }
    else {
    createEditor();
    }
    });

    function createEditor() {
    StackExchange.prepareEditor({
    heartbeatType: 'answer',
    autoActivateHeartbeat: false,
    convertImagesToLinks: true,
    noModals: true,
    showLowRepImageUploadWarning: true,
    reputationToPostImages: 10,
    bindNavPrevention: true,
    postfix: "",
    imageUploader: {
    brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
    contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
    allowUrls: true
    },
    onDemand: true,
    discardSelector: ".discard-answer"
    ,immediatelyShowMarkdownHelp:true
    });


    }
    });














    draft saved

    draft discarded


















    StackExchange.ready(
    function () {
    StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f54258241%2fwarning-iso-c-forbids-converting-a-string-constant-to-char-for-a-static-c%23new-answer', 'question_page');
    }
    );

    Post as a guest















    Required, but never shown

























    2 Answers
    2






    active

    oldest

    votes








    2 Answers
    2






    active

    oldest

    votes









    active

    oldest

    votes






    active

    oldest

    votes









    35














    constexpr does imply const, but in this case it applies const to the "wrong thing".



    constexpr char*


    is basically the same as



    char * const


    which is a constant pointer to a non-const char. This won't work because string literals have the type const char[N] so it would cast away the constness of the array elements.



    constexpr const char*


    on the other hand, is basically the same as



    char const * const


    which is a constant pointer to a constant char, which is what you want as it preserves the constness of the elements.






    share|improve this answer






























      35














      constexpr does imply const, but in this case it applies const to the "wrong thing".



      constexpr char*


      is basically the same as



      char * const


      which is a constant pointer to a non-const char. This won't work because string literals have the type const char[N] so it would cast away the constness of the array elements.



      constexpr const char*


      on the other hand, is basically the same as



      char const * const


      which is a constant pointer to a constant char, which is what you want as it preserves the constness of the elements.






      share|improve this answer




























        35












        35








        35







        constexpr does imply const, but in this case it applies const to the "wrong thing".



        constexpr char*


        is basically the same as



        char * const


        which is a constant pointer to a non-const char. This won't work because string literals have the type const char[N] so it would cast away the constness of the array elements.



        constexpr const char*


        on the other hand, is basically the same as



        char const * const


        which is a constant pointer to a constant char, which is what you want as it preserves the constness of the elements.






        share|improve this answer















        constexpr does imply const, but in this case it applies const to the "wrong thing".



        constexpr char*


        is basically the same as



        char * const


        which is a constant pointer to a non-const char. This won't work because string literals have the type const char[N] so it would cast away the constness of the array elements.



        constexpr const char*


        on the other hand, is basically the same as



        char const * const


        which is a constant pointer to a constant char, which is what you want as it preserves the constness of the elements.







        share|improve this answer














        share|improve this answer



        share|improve this answer








        edited 10 hours ago









        Remy Lebeau

        332k18251446




        332k18251446










        answered 11 hours ago









        NathanOliverNathanOliver

        89.3k15121188




        89.3k15121188

























            10














            There is a usual difference between a constant pointer and a pointer to constant. By making your constexpr char* you made a pointer itself a constexpr (and, of course, const), but it still attempts to point at non-const character - and this is wrong, as string literals are const. Solution:



            constexpr const char* ch = "StackOverflow!";


            Which declares a constexpr pointer to const.






            share|improve this answer



















            • 1





              I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

              – Eljay
              11 hours ago
















            10














            There is a usual difference between a constant pointer and a pointer to constant. By making your constexpr char* you made a pointer itself a constexpr (and, of course, const), but it still attempts to point at non-const character - and this is wrong, as string literals are const. Solution:



            constexpr const char* ch = "StackOverflow!";


            Which declares a constexpr pointer to const.






            share|improve this answer



















            • 1





              I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

              – Eljay
              11 hours ago














            10












            10








            10







            There is a usual difference between a constant pointer and a pointer to constant. By making your constexpr char* you made a pointer itself a constexpr (and, of course, const), but it still attempts to point at non-const character - and this is wrong, as string literals are const. Solution:



            constexpr const char* ch = "StackOverflow!";


            Which declares a constexpr pointer to const.






            share|improve this answer













            There is a usual difference between a constant pointer and a pointer to constant. By making your constexpr char* you made a pointer itself a constexpr (and, of course, const), but it still attempts to point at non-const character - and this is wrong, as string literals are const. Solution:



            constexpr const char* ch = "StackOverflow!";


            Which declares a constexpr pointer to const.







            share|improve this answer












            share|improve this answer



            share|improve this answer










            answered 11 hours ago









            SergeyASergeyA

            42.1k53784




            42.1k53784








            • 1





              I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

              – Eljay
              11 hours ago














            • 1





              I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

              – Eljay
              11 hours ago








            1




            1





            I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

            – Eljay
            11 hours ago





            I remember the rule const binds to the thing to its immediate left (unless its first, in which case it binds to the thing to its immediate right). In my code, I tend to favor the general case, rather than the except-to-the-general rule in the parentheses. constexpr, when I use it (not frequently), I always put on the left as the first thing. I've not been bitten by the OP's situation yet.

            – Eljay
            11 hours ago


















            draft saved

            draft discarded




















































            Thanks for contributing an answer to Stack Overflow!


            • Please be sure to answer the question. Provide details and share your research!

            But avoid



            • Asking for help, clarification, or responding to other answers.

            • Making statements based on opinion; back them up with references or personal experience.


            To learn more, see our tips on writing great answers.




            draft saved


            draft discarded














            StackExchange.ready(
            function () {
            StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f54258241%2fwarning-iso-c-forbids-converting-a-string-constant-to-char-for-a-static-c%23new-answer', 'question_page');
            }
            );

            Post as a guest















            Required, but never shown





















































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown

































            Required, but never shown














            Required, but never shown












            Required, but never shown







            Required, but never shown







            Popular posts from this blog

            SQL Server 17 - Attemping to backup to remote NAS but Access is denied

            Always On Availability groups resolving state after failover - Remote harden of transaction...

            Restoring from pg_dump with foreign key constraints