Menu

noExplicitConstructor - How to deal with intentionally implicit constructors

danpaul88
2015-05-18
2021-09-11
  • danpaul88

    danpaul88 - 2015-05-18

    Since updating to cppcheck 1.69 we've been getting a lot of new warnings for "noExplicitConstructor", most of which were in fact genuine problems. However, there are several cases where we have single parameter constructors where an implicit conversion IS acceptable for our code... yet cppcheck is still flagging these up as "errors".

    Short of adding inline suppression (which always feels "wrong" to me) what syntax would cppcheck expect to see in a constructor where the use of implicit conversions is intentionally permitted to prevent it from issuing the "noExplicitConstructor" warning?

     
  • Daniel Marjamäki

    Can you describe the use case a little.

    Can Cppcheck see that implicit conversions are intentional somehow?

    I don't like inline suppressions neither. Do you have some idea how we could do this.

     
  • danpaul88

    danpaul88 - 2015-05-22

    A simplified example from our source code;

    /*!
    * A wrapper for an MSXML::IXMLDOMNodePtr which adds extra methods to simplify some operations on the
    * XML DOM. Contains no extra member data, thus we we can freely convert between MSXML::IXMLDOMNodePtr
    * and our extended IXMLDOMNodePtrWrapper and want to permit the compiler to do so on the fly with an
    * implicit conversion
    */
    class IXMLDOMNodePtrWrapper : public MSXML::IXMLDOMNodePtr
    {
    public:
      // Constructor from base class reference
      IXMLDOMNodePtrWrapper(const IXMLDOMNodePtr& xmlNodePtr) : IXMLDOMNodePtr(xmlNodePtr) {}
    }
    

    Because the wrapper class contains no member data of its own we allow the compiler to freely convert between IXMLDOMNodePtrWrapper and MSXML::IXMLDOMNodePtr to suit whatever a given method might expect as an input.

    The problem is, how to let cppcheck know that the constructor shown above is OK to be used for an implicit conversion and thus suppress the "noExplicitConstructor" warning. I've been thinking about this for a few days now and sadly I'm not sure there is going to be any nice way to do it short of an inline-suppression... but I'd be interested to hear if anyone else has any ideas.

    It's a shame there isn't an "implicit" keyword to complement the "explicit" one, even if it served no actual purpose for the compiler and was just there to allow developers to tag deliberately implicit constructors...

     

    Last edit: danpaul88 2015-05-22
  • Daniel Marjamäki

    I got reply from the developer that wrote the explicit constructors checker:

    I am afraid that it cannot be decided by the checker. It depends on the class usage. But there is several ways how to bypass it: declare conversion operator in the IXMLDOMNodePtrclass, which will convert to the IXMLDOMNodePtrWrapperclass. Declare assign operator in the IXMLDOMNodePtrWrapperclass. The third way is to declare constructor as explicit and if there is only a few usages, use explicit object construction.

     
  • Absol

    Absol - 2021-09-10

    I got false positive with noExplicitConstructor.

    style: Class 'ClassName' has a constructor with 1 argument that is not explicit. [noExplicitConstructor]

    .h
    class ClassName
    {
    public:
        ...
        ClassName(const std::string& str);
        ...
     }
     .cpp
     ClassName::ClassName(const std::string& str)
    {
        addValue("str", str);
    }
    

    Or this is not false positive ?

     

    Last edit: Absol 2021-09-10
  • Daniel Marjamäki

    That code is exactly what the checker tries to warn about.

     
  • Absol

    Absol - 2021-09-11

    I don't know what I can do to fix code ?))))

     
  • Daniel Marjamäki

    .h

    class ClassName
    {
    public:
        ...
        explicit ClassName(const std::string& str);
        ...
     }
    
     

Log in to post a comment.

Want the latest updates on software, tech news, and AI?
Get latest updates about software, tech news, and AI from SourceForge directly in your inbox once a month.