errors result when creating header file - visual c++

S

soni29

hi,
i have written the following code, still in the learning stage:
#include<iostream.h>

class CBox {

public:
// Constructor definition
CBox(double lv, double bv = 1.0, double hv = 1.0) : m_Length(lv),
m_Breadth(bv), m_Height(hv)
{
cout << endl << "Constructor called";
}

// Default Constructor
CBox() {
cout << endl
<< "Default constructor called.";
m_Length = m_Breadth = m_Height = 1.0;
}

// Function to calculate the volume of a box
double Volume() const {
return m_Length * m_Breadth * m_Height;
}

private:
double m_Length;
double m_Breadth;
double m_Height;
};


int main() {
CBox boxes[5];
CBox cigar(8.0, 5.0, 1.0);

cout << endl
<< "Volume of boxes[3] = " << boxes[3].Volume()
<< endl
<< "Volume of cigar = " <<cigar.Volume();

cout << endl;
return 0;
}


when i try to break it into a header and source file, 2 separate
files, i get errors:
source file:
#include <iostream.h>
class CBox;

int main() {
CBox boxes[5];
CBox cigar(8.0, 5.0, 1.0);

cout << endl
<< "Volume of boxes[3] = " << boxes[3].Volume()
<< endl
<< "Volume of cigar = " <<cigar.Volume();

cout << endl;
return 0;
}


CBox.h:
#include<iostream.h>

class CBox {

public:
// Constructor definition
CBox(double lv, double bv = 1.0, double hv = 1.0) : m_Length(lv),
m_Breadth(bv), m_Height(hv)
{
cout << endl << "Constructor called";
}

// Default Constructor
CBox() {
cout << endl
<< "Default constructor called.";
m_Length = m_Breadth = m_Height = 1.0;
}

// Function to calculate the volume of a box
double Volume() const {
return m_Length * m_Breadth * m_Height;
}

private:
double m_Length;
double m_Breadth;
double m_Height;
};


\Microsoft Visual Studio .NET\Vc7\include\useoldio.h(29): warning
C4995: '_OLD_IOSTREAMS_ARE_DEPRECATED': name was marked as #pragma
deprecated
Test.cpp(5): error C2133: 'boxes' : unknown size
Test.cpp(5): error C2512: 'CBox' : no appropriate default constructor
available
Test.cpp(5): error C2262: 'boxes' : cannot be destroyed
Test.cpp(6): error C2079: 'cigar' uses undefined class 'CBox'
Test.cpp(6): error C2078: too many initializers
Test.cpp(6): warning C4244: 'initializing' : conversion from 'double'
to 'int', possible loss of data
Test.cpp(9): error C2036: 'CBox *' : unknown size
Test.cpp(9): error C2027: use of undefined type 'CBox'
Test.cpp(9): error C2228: left of '.Volume' must have
class/struct/union type
Test.cpp(11): error C2228: left of '.Volume' must have
class/struct/union type


is there a way to make it so that i can keep the files apart, if i
wanted all my classes to be in a header and the source to be separate,
please note that i wanted to make the constructors and the Volume
method inline that's why i put the code in the header.

Thank you.
 
D

David

I'm not sure of the file split, but it appears that your
"source file" didn't include cbox.h. You don't need the
"class CBox;" statement in the source file.

David

hi,
i have written the following code, still in the learning stage:
#include<iostream.h>

class CBox {

public:
// Constructor definition
CBox(double lv, double bv = 1.0, double hv = 1.0) : m_Length(lv),
m_Breadth(bv), m_Height(hv)
{
cout << endl << "Constructor called";
}

// Default Constructor
CBox() {
cout << endl
<< "Default constructor called.";
m_Length = m_Breadth = m_Height = 1.0;
}

// Function to calculate the volume of a box
double Volume() const {
return m_Length * m_Breadth * m_Height;
}

private:
double m_Length;
double m_Breadth;
double m_Height;
};


int main() {
CBox boxes[5];
CBox cigar(8.0, 5.0, 1.0);

cout << endl
<< "Volume of boxes[3] = " << boxes[3].Volume()
<< endl
<< "Volume of cigar = " <<cigar.Volume();

cout << endl;
return 0;
}


when i try to break it into a header and source file, 2 separate
files, i get errors:
source file:
#include <iostream.h>
class CBox;

int main() {
CBox boxes[5];
CBox cigar(8.0, 5.0, 1.0);

cout << endl
<< "Volume of boxes[3] = " << boxes[3].Volume()
<< endl
<< "Volume of cigar = " <<cigar.Volume();

cout << endl;
return 0;
}


CBox.h:
#include<iostream.h>

class CBox {

public:
// Constructor definition
CBox(double lv, double bv = 1.0, double hv = 1.0) : m_Length(lv),
m_Breadth(bv), m_Height(hv)
{
cout << endl << "Constructor called";
}

// Default Constructor
CBox() {
cout << endl
<< "Default constructor called.";
m_Length = m_Breadth = m_Height = 1.0;
}

// Function to calculate the volume of a box
double Volume() const {
return m_Length * m_Breadth * m_Height;
}

private:
double m_Length;
double m_Breadth;
double m_Height;
};


\Microsoft Visual Studio .NET\Vc7\include\useoldio.h(29): warning
C4995: '_OLD_IOSTREAMS_ARE_DEPRECATED': name was marked as #pragma
deprecated
Test.cpp(5): error C2133: 'boxes' : unknown size
Test.cpp(5): error C2512: 'CBox' : no appropriate default constructor
available
Test.cpp(5): error C2262: 'boxes' : cannot be destroyed
Test.cpp(6): error C2079: 'cigar' uses undefined class 'CBox'
Test.cpp(6): error C2078: too many initializers
Test.cpp(6): warning C4244: 'initializing' : conversion from 'double'
to 'int', possible loss of data
Test.cpp(9): error C2036: 'CBox *' : unknown size
Test.cpp(9): error C2027: use of undefined type 'CBox'
Test.cpp(9): error C2228: left of '.Volume' must have
class/struct/union type
Test.cpp(11): error C2228: left of '.Volume' must have
class/struct/union type


is there a way to make it so that i can keep the files apart, if i
wanted all my classes to be in a header and the source to be separate,
please note that i wanted to make the constructors and the Volume
method inline that's why i put the code in the header.

Thank you.
 
R

Rob Williscroft

soni29 wrote in
when i try to break it into a header and source file, 2 separate
files, i get errors:
source file:
#include <iostream.h>

#include <iostream> /* for std::cout */
#include said:
class CBox;

// replace with:

#include "CBox.h"
int main() {

using std::cout; /* so we can write cout instead of std::cout */
using std::endl; /* ... */
CBox boxes[5];
CBox cigar(8.0, 5.0, 1.0);

cout << endl
<< "Volume of boxes[3] = " << boxes[3].Volume()
<< endl
<< "Volume of cigar = " <<cigar.Volume();

cout << endl;
return 0;
}


CBox.h:
#include<iostream.h>

#include <iostream> /* for std::cout */
class CBox {

public:
// Constructor definition
CBox(double lv, double bv = 1.0, double hv = 1.0) : m_Length(lv),
m_Breadth(bv), m_Height(hv)
{
cout << endl << "Constructor called";

std::cout << std::endl << "Constructor called";
}

// Default Constructor
CBox() {
cout << endl

std::cout << std::endl

<< "Default constructor called.";
m_Length = m_Breadth = m_Height = 1.0;
}

// Function to calculate the volume of a box
double Volume() const {
return m_Length * m_Breadth * m_Height;
}

private:
double m_Length;
double m_Breadth;
double m_Height;
};

The main bit you were missin was #include "CBox.h".

But also note that all the C++ specific parts of the standard
library use includes without the .h suffix, also the types,
object's and function's they declare are in namespace std,
hence all "std::" prefixing I did above.


HTH

Rob.
 
J

John L Fjellstad

Rob said:
#include <iostream> /* for std::cout */
#include <ostream> /* for std::endl */

Is that really necessary? According to my "C++ Programming Language: Special
Edition" p 633: "Manipulators taking istream and ostream are presented in
<istream> and <ostream>, respectively, and also in <iostream>". std::endl
is an ostream manipulator.
Also, since std::cout is an std::eek:stream object, and is defined in
<iostream>, doesn't it follow that <ostream> has to have been included by
<iostream>?
 
R

Rob Williscroft

John L Fjellstad wrote in
Is that really necessary? According to my "C++ Programming Language:
Special Edition" p 633: "Manipulators taking istream and ostream are
presented in <istream> and <ostream>, respectively, and also in
<iostream>". std::endl is an ostream manipulator.

Logic's good so far.
Also, since std::cout is an std::eek:stream object, and is defined in
<iostream>, doesn't it follow that <ostream> has to have been included
by <iostream>?

No <iostream>

Rob.
 
R

Rob Williscroft

John L Fjellstad wrote in
My appologees for the previous post. I clicked send before
I was finnished.
Is that really necessary? According to my "C++ Programming Language:
Special Edition" p 633: "Manipulators taking istream and ostream are
presented in <istream> and <ostream>, respectively, and also in
<iostream>". std::endl is an ostream manipulator.

This is what usually happens, but it isn't what the standard says.
It's what most people (including me - untill I was told otherwise)
expect to happen.
Also, since std::cout is an std::eek:stream object, and is defined in
<iostream>, doesn't it follow that <ostream> has to have been included
by <iostream>?

<iostream> needs to declare the objects cin, cout, cerr etc.
The simplest way to do that is to:

#include <istream>
#include <ostream>

and then declare:

namespace std
{
extern istream cin;
extern ostream cout;
...
}

But it doesen't have to work like that. All it *has* to do is
include enough of the declaration's of std::basic_istream<> and
std::basic_ostream<> and possibly the typedef's std::istream and
std::eek:stream, so that it can declare the cin, cout ... objects.

It could miss out all the non-inline member defenition's.

It could also miss out defenition's for the constructor's and
destructor's for the basic_?stream<>'s even if they are inlined
as cin etc are magicly constructed before main() is entered and
aren't destroyed.

Most importantly, It dosent need to include the declaration and/or
defenition's for std::endl, std::ends, or std::flush. Firstly
because the standard dosen't require it too and secondly because
they aren't required for functioning cin, cout ... objects.

Rob.
 
A

Alf P. Steinbach

John L Fjellstad wrote in
My appologees for the previous post. I clicked send before
I was finnished.


This is what usually happens, but it isn't what the standard says.
It's what most people (including me - untill I was told otherwise)
expect to happen.


<iostream> needs to declare the objects cin, cout, cerr etc.
The simplest way to do that is to:

#include <istream>
#include <ostream>

and then declare:

namespace std
{
extern istream cin;
extern ostream cout;
...
}

But it doesen't have to work like that. All it *has* to do is
include enough of the declaration's of std::basic_istream<> and
std::basic_ostream<> and possibly the typedef's std::istream and
std::eek:stream, so that it can declare the cin, cout ... objects.

It could miss out all the non-inline member defenition's.

It could also miss out defenition's for the constructor's and
destructor's for the basic_?stream<>'s even if they are inlined
as cin etc are magicly constructed before main() is entered and
aren't destroyed.

Most importantly, It dosent need to include the declaration and/or
defenition's for std::endl, std::ends, or std::flush. Firstly
because the standard dosen't require it too and secondly because
they aren't required for functioning cin, cout ... objects.

I was simply amazed the first time I heard of this.

But it's not like it is an argument that virtually _all_ C++ textbooks,
including TCPPPL, are incorrect.

It's simply an argument that the standard has an oversight, in addition
to numerous other oversights.

We should not teach newbies to include more than <iostream> in order to
use std::cout and std::endl.

Instead, point out (if necessary) that they might run into people who
incorrectly think that the common practice is incorrect.
 
A

Alf P. Steinbach

I agree (kind off) but where do you draw the line. std::endl in
<iostream> std::make_pair in <map> or maybe:

((some_class_type)0)->some_non_virtual_member();

Some cases are not clear-cut.

Some are clearly against current practice.

The case for <iostream> is, otoh., very simple and clear: there's not
one C++ book that I know of that includes <ostream> to get std::endl.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,580
Members
45,055
Latest member
SlimSparkKetoACVReview

Latest Threads

Top