0

A simple class with explicit conversion constructor.

class MyDouble {
    double d;
public:
    MyDouble() : d(0) {}
    explicit MyDouble(double d_) : d(d_) {}
    MyDouble & operator =(double d_) {
        d = d_; return *this;
    }
};

I add an assignment on purpose to make it can be assigned constructed from double.

MyDouble a; 
a = 1.1;                    // this works
MyDouble b = MyDouble(1.1); // this works
MyDouble c(1.1);            // this works
MyDouble d = 1.1;           // this does not work 

I do not want implicit conversion, cause it will cause some other problems. But I still want direct assignment work, but it does not. Is there anyway to make the last statement MyDouble d = 1.1; work without deleting the explicit keyword.

phy nju
  • 289
  • 2
  • 7
  • 1
    The only *assignment* in your code is `a = 1.1;`. The rest are not assignment. "I do not want implicit conversion"... But `MyDouble d = 1.1;` is clearly an attempt to perform an implicit conversion! – AnT Jan 07 '18 at 07:12
  • 1
    “Explicit conversion constructor” is an oxymoron: a constructor is _converting_ iff it is not `explicit`. – Davis Herring Jan 07 '18 at 07:13
  • `MyDouble d = 1.1`; Can this be interpreted as construct a new object `d` and assign it as the number `1.1`. – phy nju Jan 07 '18 at 07:14
  • Consider that barring a new special case in the language, this would allow `vector v = 5;` to compile. – chris Jan 07 '18 at 07:14
  • Possible duplicate of [Is there a difference in C++ between copy initialization and direct initialization?](https://stackoverflow.com/questions/1051379/is-there-a-difference-in-c-between-copy-initialization-and-direct-initializati) – Silvio Mayolo Jan 07 '18 at 07:14
  • 1
    @phynju: No: initialization is not assignment. – Davis Herring Jan 07 '18 at 07:15
  • There's always the option of using `auto e = MyDouble{1.1};` That's explicit, and the type is only named once. A user defined literal may even make it nicer to look at. – StoryTeller - Unslander Monica Jan 07 '18 at 07:21
  • @phynju, How is it clearly not right? Built-in types don't have any explicitness requirements. – chris Jan 07 '18 at 07:27
  • I did not notice the type IS `double` @chris – phy nju Jan 07 '18 at 07:36
  • Quite Clear now. Thank you ALL. – phy nju Jan 07 '18 at 07:37

1 Answers1

0

The answer to your question is 'no', there is no way to allow MyDouble d = 1.; without removing the explicit.

You could simply use MyDouble d(1.); or MyDouble d{1.}; instead of using assignment-initialization. That would allow you to retain the explicit while also being clear you are initializing.

SoronelHaetir
  • 12,547
  • 1
  • 11
  • 21
  • Nit-pick: it is [*copy initialization*](http://en.cppreference.com/w/cpp/language/copy_initialization), not *assignment-initialization*. – juanchopanza Jan 07 '18 at 07:40