0

I was going through a youtube video regarding static in c++, in which I found a piece of code which is confusing me

#include<iostream>
using namespace std;

class Singleton {
    static Singleton* s_instance;
public:
    static Singleton& Get() { return *s_instance; }

    void display() {
        cout << "Hello" << endl;
    }

};
Singleton* Singleton::s_instance=nullptr;

int main() {
    Singleton::Get().display();
}

I wonder why compiler doesn't give an error since we are returning a dereferenced nullptr object in Get() function. Also when I tried the same, but with return type of Get() func set to just Singleton instead of Singleton&, the compiler does throw an error stating that s_instance is a nullptr. Can you explain if the reference return type of Get() func has something to do with this?

Dexter
  • 11
  • Dereferencing a nullptr is undefined behaviour, anything can happen. – Quimby Jul 01 '21 at 10:55
  • Related: [Why is dereferencing of nullptr while using a static method not undefined behavior](https://stackoverflow.com/questions/63331787/why-is-dereferencing-of-nullptr-while-using-a-static-method-not-undefined-behavi). – rawrex Jul 01 '21 at 10:58
  • 2
    Note that this isn't a static method, but it happens not to actually look at the instance pointed to by `this` at all, so it gets away with it. It's still UB, and the compiler is not required to detect or issue a diagnostic for UB. – Useless Jul 01 '21 at 11:00
  • Often, when you dereference a pointer, nothing observably bad happens until you actually try to use the object that doesn't exist. For instance, when you copy it. (Dereferencing a pointer does not necessarily involve reading anything from memory.) – molbdnilo Jul 01 '21 at 11:02
  • 1
    The behaviour of your code is undefined due to dereferencing a null pointer. The standard does not require diagnostics (e.g. error or warning messages) to be produced for undefined behaviour. – Peter Jul 01 '21 at 11:10
  • @molbdnilo , If I am understanding it correctly since we are not returning the copy of s_instance, thus we escape from compiler throwing an error i.e our instance is never really used. – Dexter Jul 01 '21 at 11:10
  • 1
    @HarshababSingh Almost, but not exactly. The compiler has nothing to do with runtime errors. Basically, determining wether `return *s_instance;` is valid or not is not possible at compile time, so the compiler is not required to issue an error or warning. But at runtime this expression invokes undefined behavior, meaning anything might happen. Usually this will just crash and many systems will provide a error message. – Lukas-T Jul 01 '21 at 11:21
  • It's undefined behavior, anything can happen. And "look, it works nevertheless!" is one of the possible things that is meant by "anything". – j6t Jul 01 '21 at 11:25
  • Crashes on my machine due to referencing binding to a nullptr. – Eljay Jul 01 '21 at 14:16
  • If you think of a reference as a pointer-with-different-syntax (not exactly correct, but a close approximation), you might come up with a reason why, *on your system*, returning by reference was no more problematic than returning a null pointer would have been. (It is illegal to construct a "null reference", but at the same time no compiler is required to add runtime checks to prevent it.) – JaMiT Jul 02 '21 at 02:27

0 Answers0