C++: Is this Valid? Wrapper Class Reference Type Conversion

  • C/C++
  • Thread starter Hurkyl
  • Start date
In summary: There's a few classes in there that do exactly this sort of thing, and you can look at the source to see how they did it, too.What exactly is this operator returning? It's currently untyped.
  • #1
Hurkyl
Staff Emeritus
Science Advisor
Gold Member
14,981
26
Allow me to present a simplified version of what I'm doing: (yes, I have a reason to do this. :tongue2:)

Code:
class wrapper
{
private:
	int &v;
public:
	wrapper(int &value):v(value) {}
	wrapper& operator=(int value) {
		v = value;
		return *this;
	}

	// This is the questionable bit:
	operator wrapper&() { return *this; }
};

wrapper make_wrapper(int &value)
{
	return wrapper(value);
}

template <typename T>
void foo(T &t)
{
	t = 1;
}

int main()
{
	int x;
	foo(make_wrapper(x));	
}

To summarize:

I wish to create a class that acts as a reference type.
I would like to be able to pass my custom reference type into any template function that expects an actual reference.

But here's the problem: C++ doesn't let you make a non-constant reference to a temporary object.

Since it would be rather painful for me to overload every function I might ever want to call to take any combination of the reference types I'm writing, and for every function I develop to have multiple versions, I would like a more automatic approach.

Thus, I provided a conversion into (wrapper&). g++, at least, is happy with it.

Is this valid C++?
 
Technology news on Phys.org
  • #2
hmmm... well, if gcc has no issues with it then it must work ok. I know gcc is not yet perfect with respect to the ANSI standard, but oh well.
 
  • #3
Code:
class wrapper
{
private:
int &v;
public:
wrapper(int &value):v(value) {}
wrapper& operator=(int value) {
v = value;
return *this;
}
// This is the questionable bit:
operator wrapper&() { return *this; }
};
wrapper make_wrapper(int &value)
{
return wrapper(value);
}
template <typename T>
void foo(T &t)
{
t = 1;
}
int main()
{
int x;
foo(make_wrapper(x));	
}
To summarize:
[/QUOTE]

operator wrapper&() { return *this; }
i don't understand this, can you return an operator?(not that i know of) if you can the this pointer is a pointer to a class and not an operator.
maybe you mean
wrapper operator&(){ return *this; }
 
Last edited:
  • #4
operator wrapper& is a conversion operator, like operator int, or operator char. It allows you to convert an object of type wrapper into an object of type wrapper&
 
  • #5
hmmm... well, if gcc has no issues with it then it must work ok. I know gcc is not yet perfect with respect to the ANSI standard, but oh well.
I'm mainly worried if the behavior is undefined, so that I can't expect it to work in general. =(
 
  • #6
hmmm i havnt seen this before an can't seem to find anything in stroustrup's book have to got a link to an example or something please thanks.
 
  • #7
hmmm i havnt seen this before an can't seem to find anything in stroustrup's book have to got a link to an example or something please thanks.

edit.
hmmm now i see, sorry about that
 
  • #8
dmail try looking under type casting...cuz that's what your basically doing

you can overload int and double's i believe...i use the typdef double REAL

and you can basically do (REAL*)vector...to get teh ntuple outta class vector.
so if you store an array in teh class
you can do operator REAL*() { return _a; } where _a is teh array. and thus you leave out the remainder of the class.

why do you need ansi standards hurkyl...can't you test it out on your compiler?
 
  • #9
Because it's nice to have code that relies only on defined behavior. :tongue2: This isn't solely for personal use -- I expect others to be able to use this as well.
 
Last edited:
  • #10
If you compile with gcc you can pass the -ansi parameter and it force the standard. You may also need to use the __STRICT_ANSI__ macro.
 
  • #11
Well, I suspect the syntax is valid, I'm more worried about the semantics -- whether I can be guaranteed that my object will live while I pass the reference around... -ansi doesn't guarantee me that, does it?
 
  • #12
Oh wait... I figured out how I can figure this out. I just need to make the destructor do something... gcc will surely put the destructor call exactly where it's supposed to go, right? Or is gcc allowed to wait for a more convenient time?
 
  • #13
Code:
// This is the questionable bit:
operator wrapper&() { return *this; }

What exactly is this operator returning? It's currently untyped.
Other than that, returning *this is perfectly fine, IIRC. You just need to make sure that you don't access the memory after your object has been deleted.

I wish to create a class that acts as a reference type.

Unless this is just for fun, check out the boost library. There's a few classes in there that do exactly this sort of thing, and you can look at the source to see how they did it, too.
 
  • #14
What exactly is this operator returning? It's currently untyped.
It's a conversion operator, syntactically no different than saying operator int(): it says that the compiler may use this operator to implicitly convert anything of type wrapper into one of type wrapper&.

You just need to make sure that you don't access the memory after your object has been deleted.
Right, and my big question is when it gets deleted! I've since run my experiment, and it seems that the lifetime of the temporary is sufficiently long for my purposes (assuming that the compiler called the destructor at the earliest legal opportunity).

Unless this is just for fun, check out the boost library. There's a few classes in there that do exactly this sort of thing, and you can look at the source to see how they did it, too.
Which classes in particular?
 
  • #15
Hurkyl said:
Oh wait... I figured out how I can figure this out. I just need to make the destructor do something... gcc will surely put the destructor call exactly where it's supposed to go, right? Or is gcc allowed to wait for a more convenient time?

Destructors are called deterministically. When a stack-based object goes out of scope, its destructor is called immediately.

I think what you're doing is undefined behaviour. Your operator wrapper& is fine, but I don't think it's valid to return a reference to a temporary; I think that the temporary is created on the stack, and so any reference to it becomes invalid as soon as make_wrapper returns. I'm not sure, though. It's been a while since I had to think about the object creation rules in C++.
 
  • #16
Hurkyl said:
It's a conversion operator, syntactically no different than saying operator int(): it says that the compiler may use this operator to implicitly convert anything of type wrapper into one of type wrapper&.

Yes, I know that. I just got mixed up and thought that it should be explicitly stated that it is returning something. Apparently conversion operators don't have to have an explicitly stated return type.

Which classes in particular?

http://www.boost.org/libs/smart_ptr/smart_ptr.htm" [Broken]
 
Last edited by a moderator:

1. Is it possible to convert a wrapper class to a reference type in C++?

Yes, it is possible to convert a wrapper class to a reference type in C++ by using the dereference operator (*). This operator allows you to access the underlying reference type value of the wrapper class.

2. How do you declare a wrapper class in C++?

To declare a wrapper class in C++, you would use the keyword "class" followed by the name of the wrapper class and a pair of curly braces to enclose the class definition. You can also include member variables and functions within the class definition.

3. Can a wrapper class hold a reference type in C++?

Yes, a wrapper class can hold a reference type in C++. This is one of the main purposes of a wrapper class, to wrap a reference type and provide additional functionality or abstraction.

4. How do you convert a reference type to a wrapper class in C++?

To convert a reference type to a wrapper class in C++, you can use the constructor of the wrapper class. This allows you to initialize the wrapper class with the value of the reference type.

5. What is the purpose of using a wrapper class in C++?

The main purpose of using a wrapper class in C++ is to provide additional functionality or abstraction for a reference type. This can include things like error handling, memory management, or operator overloading.

Similar threads

  • Programming and Computer Science
Replies
1
Views
568
  • Programming and Computer Science
Replies
2
Views
649
Replies
63
Views
3K
  • Programming and Computer Science
Replies
31
Views
2K
  • Programming and Computer Science
Replies
19
Views
2K
  • Programming and Computer Science
2
Replies
35
Views
2K
  • Programming and Computer Science
Replies
25
Views
1K
  • Programming and Computer Science
Replies
34
Views
2K
  • Programming and Computer Science
Replies
11
Views
947
  • Programming and Computer Science
Replies
17
Views
1K
Back
Top