1

I have the following code:

    struct Y {
        string& s1; //string s1; throws no error
        Y( string src ) : s1(src) { cout<<"s1: "<<s1<<endl; }
        void show(){ cout<<s1<<endl; }
    };

    int main()
    {
        Y y1("Krypton");
        y1.show(); //run-time error
    }

y1.show() should display "Krypton", but I get a runtime error (due to s1 being uninitialized when y1.show() is being called?).

Q1. Why would s1 be uninitialized when it has already been initialized in the constructor initialization list? Q2. Why don't I get the same error if I use string s1; instead of the reference?

Any help would be greatly appreciated.

Regards,

Jay.

1
  • 1
    It is usually a good idea to describe the actual error, rather than just saying "I get a runtime error". Commented Jul 7, 2013 at 9:47

4 Answers 4

1

You are initializing a reference from a temporary. If you want instances of struct Y to hold an actual string, rather than just a reference, you need a member variable of type string, not reference to string.

Q1. Why would s1 be uninitialized when it has already been initialized in the constructor initialization list?

It was initialized, but to be a reference to a string that no longer exists.

Q2. Why don't I get the same error if I use string s1; instead of the reference?

If the class contains a string, then it doesn't contain a reference to a string that exists.

What string do you think the reference is a reference to?

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks. So if I understand this correctly, the reference member pointed to a value that did not exist once the constructor execution was complete. But reference variables have to be initialized in the initialization list. In that case, how can I initialize s1 correctly?
It ceased to exist as soon as this line of code completed Y y1("Krypton");. Because you passed the constructor a const char *, it had to create a temporary string. That temporary ceased to exist as soon as it was no longer needed. When you take a reference to an object, it is your responsibility to ensure the reference isn't dereferenced after the object ceases to exist!
1

s1 is set to reference src, which is a temporary object and is destroyed when the constructor exists.

When you make s1 a string, it is a local copy that doesn't depend on src

Comments

0

Because your constructor Y(string src) accepted a template value, and s1 reference to this template value, and then you call show() print the value witch is destroty after constructor.

Answer:

1.Because the value s1 referenced is destroy after constructor.

2.If you use string s1 instead of string& s1, witch assign src yo s1 when call constructor, and show() will print the member value of s1.

If you want to pring "Krypton", you can change Y( string src ) to Y( string& src )

Comments

0

In your case you can initialize the temporary member variable like this

struct Y 
{
    string& s1;

    Y( string& src )
        : s1(src)
    {
        cout<<"s1: "<<s1<<endl;
    }

    void show()
    {
        cout<<s1<<endl;
    }
};

int main()
{
    string s1_real = "Krypton";
    Y y1(s1_real);
    y1.show();

    return 0;
}

Note that

  1. Constructor takes a reference (string& src not string src). Because if you use "string src" it will be a temporary variable which will be destroyed as soon as the function stack unwinds and s1 ends up being a dangling reference. If you use "string& src" there is no new memory location created; src points to s1_real and therefore s1 ends up pointing to s1_real.

  2. You create a variable (s1_real) which is used to create y1. This is because you can't take a reference of a temporary variable (you can only take a const reference, in which case src and s1 too must be declared as const references)

Always note that the lifetime of y1 must be less than that of s1_real or else y1.s1 ends up being a dangling reference

1 Comment

Thanks John! I'd had the same line of thought, however had missed changing the ctor to accept reference to the string defined in main(). So it was still crashing, again due to all of the reasons explained above :)

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.