Reputation: 122500
I have a struct Foo
. In pseudocode:
def FindFoo:
foo = results of search
foundFoo = true if a valid foo has been found
return foo if foundFoo else someErrorCode
How can I accomplish this in C++?
Edited to remove numerous inaccuracies.
Upvotes: 10
Views: 21611
Reputation: 6208
Is not finding a foo really an exceptional situation? Then throw an exception. Expect to not find foo? have the function return an error code and pass the foo out via a reference parameter, where foo is only valid if the function returns no error.
Upvotes: 0
Reputation: 11515
It's not possible in C++ without resorting to pointers or a library solution outside the standard library. (Boost is not a part of the standard library, it's a 3rd party solution.)
In C#, you can use a Nullable<Foo>
.
Contrary to Billy's comment, structs are value types, not reference types, and Nullable can be applied to any value type, not just built-ins. The following compiles just fine:
struct Test {
int Blah;
}
void Main() {
System.Nullable<Test> proof;
}
Upvotes: 0
Reputation: 263158
You can look into boost::optional
and see if it fits your needs. However:
return foo if foundFoo else someErrorCode
This makes me think that you might be better off throwing an exception if you don't find foo.
Upvotes: 3
Reputation: 61815
You cant do this in C# either - you would need to return new Foo()
, not null
to make the compiler happy.
Ditto the C++ case - you need to instantiate a struct if you're going to return by value. If not, you want to return by pointer (in which case you'd be new
ing or returning a pointer to one allocated in another manner, which brings messy ownership transfer semantics into the equation).
EDIT: Based on your update. It seems you want to return either a value or a 'null' meta-value that indicates 'not found'. You can do this in a number of ways:
throw
if it fails, otherwise unconditionally return a valuedelet
ing it up in the air if it's not something that's going to stay in memory long termNullable<T>
would (I'll let someone chime in with the right one UPDATE: @Mike Seymour says it's boost::optional<foo>
)Upvotes: -1
Reputation: 9866
One way of doing it is to return a pointer to a foo:
public Foo* findFoo()
{
return fooFound ? new fooResult() : NULL;
}
Another possibility to define a NullFoo
of some kind, possibly as a struct
extending Foo
with an empty implementation. For more information about the latter idea, you can read about the Null Object Pattern.
Edit: The modified question is somewhat different, and as other people have mentioned, you may be best off throwing an exception rather than doing either of the above.
Upvotes: 2
Reputation: 503983
C++ objects can never be null or empty. Pointers can hold a null pointer value indicating they point at nothing.
The typical solution would be to throw an exception. Otherwise, use a pointer; just make sure you aren't returning the address of a temporary.
I wouldn't recommend trying to teach yourself C++ with knowledge from other languages, you'll hurt yourself. Grab a good beginner-level book, it's the best way to learn.
Upvotes: 14
Reputation: 284836
That doesn't work in C# either. You should return a pointer to Foo.
Upvotes: 0