I've encountered this code example and I remembered I've seen it before and I didn't know what it is for and what it does? I've searched on the internet but without luck.
Code:
class C
{
int x; // a non-static variable, implicitly private
public:
C() : x(0) {} // default constructor
// a static member function, which uses a non-static variable perfectly well
static int Incr(C& instance) { return ++(instance.x); }
} g_c;
int main(void)
{
C c2;
return C::Incr(g_c) + C::Incr(c2);
}
What does g_c after the last class bracket means?
} g_c;
Here g_c is declared to be an object of the class type C.
Such construct enables you to create object(s) of unnamed type as:
class //Nameless class!
{
//data members
}obj1, obj2;
In this example, obj1 and obj2 are declared to be objects of a class type which has not been given any name — the class is nameless! In such situation, you cannot declare objects in a conventional sense (i.e Type obj1, obj2; sense). So this construct helps you do that.
You can even derive from other named classes while being nameless (and declaring the objects of the nameless class):
class : public A, public B //Nameless class is deriving from A and B
{
//data members
}obj1, obj2;
In short, this construct ensures that the user wouldn't be able to create more objects than intended, unless some evil programmer uses/misuses/abuses C++11 (or template) as:
decltype(obj1) obj3; //hehe!
Hope that helps!
It's shorthand for:
class C
{
....
};
C g_c;
You declare variables using the format type variable_name;. For example:
A x;
Where A may be the name of a class.
But instead of using a pre-existing class type, you can also define the class at the same time as you declare a variable of the new class's type:
class { ... } x;
or define the class and give it a name:
class A { ... } x;
In C++ it is common to just define the class and give it a name, but leave off the variable:
class A { ... };
but you don't have to leave off the variable.
That's just a way of creating objects of that type of Class. Structs mostly use them to initialize new variables.
Related
The code below compiles just fine (unless the call to method is uncommented).
Why is it allowed to "call" to the default constructor? (there shouldn't be one)
Why is the declaration of the member function not an error?
.
extern "C"
{
struct S
{
int some_int;
void method(){}
};
}
int main()
{
S s();
// s.method();
return 0;
}
First, S s(); declares a function named s that takes no arguments and returns an object of type S. Just like int f();.
Second, that extern "C" isn't relevant here. It's used, roughly, for functions that are written in C and called from C++. It doesn't mean "pretend that this code is C code".
Third, S does have a default constructor. The compiler generates one. In this case it doesn't do anything, because there are no members of S that require non-trivial initialization. To use the default constructor you'd write S s; or S s{};.
Fourth, the reason that declaring a member function is okay is that a struct and a class in C++ can have member functions. I know, that sounds tautologous, but it's important to keep in mind that a struct can have member functions, static data, private, protected, and public members just like a class. The only differences between a struct and a class is that by default members of a class are private while members of a struct are public, and by default a base of a class is inherited privately while a base of a struct is inherited publicly.
Adding a default constructor (although it's optional here) and using curly-braces rather than parenthesis or you don't even need to use that, will solve your issue:
....
struct S {
S() {} // declaring the constructor explicitly here
};
....
int main(void) {
S s{}; // Don't use s() - a function, instead, call the
// default constructor
// S s;
s.method();
return 0;
}
Well, just new in classes and trying to create a simple program, that has 2 classes. Class A and Class B. Well I'm trying to initialize my variable in constructor in class A, and then make some action and pass it to class B, where I'm also can make some action. So class A is a base class. However, when I compile the program I got two mistake -
error: ‘i’ was not declared in this scope
For class A and class B. So I have two question 1) why constructor doesn't declare variables (according to the books constructor called first)? 2) what ways I can transfer the variable from class A to use in class B?
#include <iostream>
#include <cstdio>
using namespace std;
class A {
public:
A(){
int i =1;
}
~A(){}
int foo () {
int p = i+1;
i++;
return p;
}
};
class B : public A {
public:
int showme() {
return i;
}
};
int main() {
A j;
B k;
cout<< k.showme()<<endl;
cout<< j.foo()<<endl;
return 0;
}
First off, get a good book:
The Definitive C++ Book Guide and List
and familiarize yourself with the basics. Your question indicates there is a complete mess right now in your understanding of C++.
Now on to the actual Q's.
1) C-tor does not declare a class member variable, it can only declare a local variable since a c-tor is also a function. You need to declare the member variable explicitly like so:
class A {
int i;
public:
A(int _i): i(_i) { }
};
2) The term "transfer" is incorrect per se. In this case, the two classes are in an inheritance hierarchy, so the variable i is inherited by class B and if you declare it as protected, then it will be accessible in the way you do it. The function B::showme() is defined correctly. Fix the first part and the example is going to work.
3) Do not confuse classes and objects. When there is an object of class A declared, it is in no way related to another object of class A or B. j and k share their own private instances of int i (provided that you fix (a)) and if you want to have k's instance of i to be equal to that of j, you can e.g. implement a copy constructor or a pair of getter/setter functions.
Suppose I have class B which gets a value 'v' in the constructor from another class A. How can I read this value from class C?
Class C will be instantiated on demand, but A has created B and passed the 'v' already. 'v' will change in every instantiation. I have tried to make 'v' static in Class B. Would it work? I could not implement it properly.
Class A {
public:
int* v;
B b1;
A(int* var) : v(var), b1(var) {};
}
How to access the same version of 'v' from a C class?
I can define B and C however I like in order to achieve the goal. But I cannot change A for that purpose.
You need a (public) static member
class A { //let's stick with your naming convention!
public:
static int a;
}
A::a = 4;
However allowing people to change A::a means that your program will probably end up relying on a global unencapsulated state... which is usually a sign of a bad design.
If you member was const however you are really relating a constant to your class, which is not so bad.
class A {
public:
static const int a = 4;
}
std::cout << "A:a is always " << A::a << std::endl;
EDIT BASED ON UPDATED QUESTION
If you require help with building a class I would recommend that you use a factory of some kind. If I understand your requirement you want to be able to inject a value into every class A and class B instance. This value "v" is based on a Class C.
So...
class C {
private:
// up to you where you implement the getUniqueNumberForNow function
// (global free function for example)
static const int v = getUniqueNumberForNow();
public:
static A createA(){
return A(v);
}
static B createB(){
return B(v);
}
}
The getUniqueNumberForNow() function just gets whatever your value should be. It will be then stored in class C and can be used during the creation of A an\or B. Now just make A and B's CTORs private and make C a friend of both and you will have only one way to create an A or B, and it will always use the correct value.
See NeilMonday's link in the comments below for info on friend classes.
Last thing is if you want to have the value change for every instantiation of A you can just do this in the factory:
static A createA(){
return A(getUniqueNumberForNow());
}
However if that is really what you want then just do this:
class A {
public:
A() : val (getUniqueNumberForNow()), b(B(val)){}
}
You cannot access a 'v' which has never passed to the class. Instead you can make a static copy of it as a member in your class A. It will update every time A is instantiated like this:
Class A {
public:
int* v;
static int* staticv;
...// Constructor etc
}
in your .cc code of A:
int* A::staticv;
...
A::staticv=this->v;
now any class can access to this value by:
A::staticv;
We can not create an object of abstract class. And constructors create new instances of any class which is called as an object.
This is what I know about the constructor, class and object relationship.
Please correct me if I am wrong.
Does it exist?
#include <iostream>
class A
{
public:
virtual void f() = 0;
A()
{
std::cout << "Yes it does!" << std::endl;
}
};
class B: public A
{
public:
void f() {}
};
int main()
{
B b;
return 0;
}
Yes it does!
The technical reason is that somebody needs to initialize the members of A and that's the job of the constructor. But you can easily reason it as follows:
The inheritance relation is often termed with "is". For example, an object of type B is also of type A. In other words B is a kind of A. The constructor of A constructs an object of type A. But b above is also a kind of A, so A must have a constructor to be able to construct it.
Yes! It has to exist, since constructors of any child class make a call to the base constructor. (This is the simplest way to explain it)
Does “Constructor of an abstract class” exists?
Let's say that there can be an abstract class constructor. Just like any other class. By default (if you don't declare a "custom" constructor or you don't have member objects that have no default constructor) there are two implicitly defined: the default constructor and the copy constructor.
So in a declaration like this:
struct abstract_class {
virtual void func() = 0;
}
you still have constructors.
We can not create an object of abstract class.
Yes. For the most common definition of abstract class, that is true. If a class does have pure virtual functions, it is considered to be an abstract class and of course it cannot be instantiated.
And constructors create new instances of any class which is called as an object.
I'd rephrase that to: You construct objects of a class type via their constructor. And yes, in C++, an object is (from §1.8/1):
An object is a region of storage.
And that's that. For example:
int x = 0;
is an object too. An object does not necessarily mean a class type.
Abstract classes can contain member variables and to initialize those member variables Abstract classes need constructor.
I've encountered this code example and I remembered I've seen it before and I didn't know what it is for and what it does? I've searched on the internet but without luck.
Code:
class C
{
int x; // a non-static variable, implicitly private
public:
C() : x(0) {} // default constructor
// a static member function, which uses a non-static variable perfectly well
static int Incr(C& instance) { return ++(instance.x); }
} g_c;
int main(void)
{
C c2;
return C::Incr(g_c) + C::Incr(c2);
}
What does g_c after the last class bracket means?
} g_c;
Here g_c is declared to be an object of the class type C.
Such construct enables you to create object(s) of unnamed type as:
class //Nameless class!
{
//data members
}obj1, obj2;
In this example, obj1 and obj2 are declared to be objects of a class type which has not been given any name — the class is nameless! In such situation, you cannot declare objects in a conventional sense (i.e Type obj1, obj2; sense). So this construct helps you do that.
You can even derive from other named classes while being nameless (and declaring the objects of the nameless class):
class : public A, public B //Nameless class is deriving from A and B
{
//data members
}obj1, obj2;
In short, this construct ensures that the user wouldn't be able to create more objects than intended, unless some evil programmer uses/misuses/abuses C++11 (or template) as:
decltype(obj1) obj3; //hehe!
Hope that helps!
It's shorthand for:
class C
{
....
};
C g_c;
You declare variables using the format type variable_name;. For example:
A x;
Where A may be the name of a class.
But instead of using a pre-existing class type, you can also define the class at the same time as you declare a variable of the new class's type:
class { ... } x;
or define the class and give it a name:
class A { ... } x;
In C++ it is common to just define the class and give it a name, but leave off the variable:
class A { ... };
but you don't have to leave off the variable.
That's just a way of creating objects of that type of Class. Structs mostly use them to initialize new variables.