I have:
struct Foo {
std::string first_name;
std::string last_name;
int age;
};
void DoFoo(const Foo& foo) {...}
I am writing tests for DoFoo
and I would like to have default values for the members of Foo
:
Foo default_foo = {.first_name = "John", .last_name = "Doe", .age = 42};
Then I have test testing different values, for example:
TestInvalidAge() {
Foo my_foo = default_foo;
my_foo.age = -1;
ASSERT_FAILS(DoFoo(my_foo));
}
This syntax is annoying because it is verbose to keep copying Foo my_foo = default_foo
in every test case. I was wondering if there is a way to get the following syntax to work:
struct TestFoo : public Foo {
// Somehow set first_name to "John", last_name to "Doe" and age to 42.
}
TestInvalidAge() {
ASSERT_FAILS(DoFoo(TestFoo{.age = -1}));
}
I don't know how to override and set the default values of base members.
I tried using a default constructor for TestFoo
in https://onlinegdb.com/tHxetZ6u5 but then the TestFoo{.age = -1}
syntax doesn't work and I have to write:
TestFoo my_foo = TestFoo();
my_foo.age = -1;
Which is exactly the syntax I was trying to avoid.
CodePudding user response:
You could initalize the base class in the TestFoo
default constructor:
struct TestFoo : public Foo {
TestFoo() : Foo{"John", "Doe", 42} {}
// possibility to use a different age:
TestFoo(int Age) : TestFoo() {
age = Age;
}
};
Another option:
struct TestFoo : public Foo {
TestFoo() : Foo{"John", "Doe", 42} {}
TestFoo(const Foo& rhs) : TestFoo() {
if(!rhs.first_name.empty()) first_name = rhs.first_name;
if(!rhs.last_name.empty()) last_name = rhs.last_name;
if(rhs.age) age = rhs.age;
}
};
DoFoo(TestFoo{} = Foo{.age = -1});
CodePudding user response:
You can use in-class initializers. They are used as default when no other initializer is provided:
#include <string>
#include <iostream>
struct Foo {
std::string first_name = "Peter";
std::string last_name = "Parker";
int age = 42;
};
int main(){
Foo f{.age = 12};
std::cout << f.first_name << " " << f.last_name;
}