c++c++17visual-studio-2019gcc8

steady_clock::now() return type invalid with gcc


I have the following code:

#include <chrono>

struct SteadyTime : std::chrono::steady_clock::time_point {
    using time_point::time_point;

    static SteadyTime now() {
      return clock::now();
    }
};

This works well with Visual Studio 2019 but with gcc 8.3 I get the following error:

<source>: In static member function 'static SteadyTime SteadyTime::now()':

<source>:7:24: error: could not convert 'std::chrono::_V2::steady_clock::now()' from 'std::chrono::_V2::steady_clock::time_point' {aka 'std::chrono::time_point<std::chrono::_V2::steady_clock, std::chrono::duration<long int, std::ratio<1, 1000000000> > >'} to 'SteadyTime'

       return clock::now();

              ~~~~~~~~~~^~

Compiler returned: 1

This code seems to be standard so what could be wrong?


Solution

  • What you are trying to do is essentially this:

    struct Base
    {};
    
    Base getBase();
    
    struct Derived : Base
    {
        static Derived get() { return getBase(); }
    };
    

    https://godbolt.org/z/KZyP99

    That doesn't work because the compiler has no idea how to convert a Base to a Derived. You could add a constructor for Derived from Base to fix this.

    I would question the general design though. Inheriting from std facilities is generally a design flaw/weakness. Prefer composition over inheritance (especially if the thing you intend to derive from is not polymorphic). Have SteadyTime expose a time_point member if you need to, or wrap its interface manually. Having and using multiple concrete (i.e. non-abstract) classes in the same inheritance hierarchy quickly leads to chaos like object slicing and other UB, as well as general confusion for users.