Newbie: Cancelling the creation of a class object - c++
This is a discussion on Newbie: Cancelling the creation of a class object - c++ ; Is it possible to cancel or prevent the creation of a class object?
I have a fileClass which has a default and non-default constructor
(fileName provided as argument). If no fileName is provided or the
provided fileName does not exist ...
-
Newbie: Cancelling the creation of a class object
Is it possible to cancel or prevent the creation of a class object?
I have a fileClass which has a default and non-default constructor
(fileName provided as argument). If no fileName is provided or the
provided fileName does not exist or cannot be opened for reading, I
would like to cancel the creation of the class object.
Is this possible, if so, how?
(I would prefer, if possible to do the test at the class level, rather
than test for a fileName in the program proper and only if successful
create the object.)
class fileStream
{
public:
//default constructor
fileStream();
//constructor with filename
fileStream(const string &fileName);
//destructor
~fileStream() {if (inFile.is_open()) inFile.close( );}
private:
//the input file stream for reading from the file
ifstream inFile;
};
//--------------------------------------------------------
//default constructor
//--------------------------------------------------------
fileStream::fileStream()
{
//how do I cancel the construction of an object?
}
//--------------------------------------------------------
//non-default constructor, fileName provided
//--------------------------------------------------------
fileStream::fileStream(const string &fileName)
{
if (fileName!="")
{
try
{
//attempt to open the file
inFile.open(fileName.c_str());
}
catch (...)
{
//how do I cancel the construction of an object?
//if the file cannot be opened or not found
cout << "\aERROR : \"" << fileName << "\" cannot be found or opened."
<< endl;
}
}
}
-
Re: Newbie: Cancelling the creation of a class object
* TreatmentPlant:
> Is it possible to cancel or prevent the creation of a class object?
Yes, by throwing an exception.
> I have a fileClass which has a default and non-default constructor
> (fileName provided as argument). If no fileName is provided or the
> provided fileName does not exist or cannot be opened for reading, I
> would like to cancel the creation of the class object.
>
> Is this possible, if so, how?
Yes (see above), but do note that /unless you use advanced techniques/
you will not thereby simplify the class' other code, which must still
check for failure at every point, because file operations may fail at
any time -- e.g., the file may reside on removable storage...
Objects that represent files therefore usuallt have a nullstate or error
states.
E.g., std::ifstream -- although that's not a very design overall, it's
use of a logical error state (nothing happens in that state) is typical.
--
A: Because it messes up the order in which people normally read text.
Q: Why is it such a bad thing?
A: Top-posting.
Q: What is the most annoying thing on usenet and in e-mail?
-
Re: Newbie: Cancelling the creation of a class object
TreatmentPlant wrote:
> Is it possible to cancel or prevent the creation of a class object?
>
> I have a fileClass which has a default and non-default constructor
> (fileName provided as argument). If no fileName is provided or the
> provided fileName does not exist or cannot be opened for reading, I
> would like to cancel the creation of the class object.
>
> Is this possible, if so, how?
Yes, it is possible.
If you want to require a fileName to be passed to the constructor, you
should not provide a default constructor. This way, the compiler will
barf if someone tries to create an object without passing a fileName.
If the constructor then finds out that the file can not be opened, you
throw an exception to abort the construction of the object.
>
> (I would prefer, if possible to do the test at the class level, rather
> than test for a fileName in the program proper and only if successful
> create the object.)
>
>
> class fileStream
> {
> public:
>
> //default constructor
> fileStream();
Leave this one out.
>
> //constructor with filename
> fileStream(const string &fileName);
>
> //destructor
> ~fileStream() {if (inFile.is_open()) inFile.close( );}
>
> private:
>
> //the input file stream for reading from the file
> ifstream inFile;
> };
>
>
> //--------------------------------------------------------
> //default constructor
> //--------------------------------------------------------
> fileStream::fileStream()
> {
> //how do I cancel the construction of an object?
It is better to avoid getting here in the first place.
If you provide at least one constructor yourself (like the one below),
then the compiler will not automagically generate a default
constructor. This forces all client code to use the constructor that
takes a fileName argument.
> }
>
> //--------------------------------------------------------
> //non-default constructor, fileName provided
> //--------------------------------------------------------
> fileStream::fileStream(const string &fileName)
> {
> if (fileName!="")
> {
> try
> {
> //attempt to open the file
> inFile.open(fileName.c_str());
Unless you tell the inFile object explicitly to do so, this will not
throw an exception if opening the file fails.
The reason for this is that failure to open a file is usually no
exceptional behaviour. And even if opening succeeded, there may be
external conditions that render the file unreadable (think: removing
the disk from the system for example).
To abort the construction, throw an exception:
if (! inFile.is_open() )
{
istringstream iss;
iss << "\aERROR : \"" << fileName << "\" cannot be found or opened."
throw std::ios::failure(iss.str());
}
> }
> catch (...)
> {
> //how do I cancel the construction of an object?
>
> //if the file cannot be opened or not found
> cout << "\aERROR : \"" << fileName << "\" cannot be found or opened."
> << endl;
> }
> }
> }
Bart v Ingen Schenau
--
a.c.l.l.c-c++ FAQ: http://www.comeaucomputing.com/learn/faq
c.l.c FAQ: http://www.eskimo.com/~scs/C-faq/top.html
c.l.c++ FAQ: http://www.parashift.com/c++-faq-lite/
-
Re: Newbie: Cancelling the creation of a class object
TreatmentPlant wrote:
> Is it possible to cancel or prevent the creation of a class object?
Others already told you how.
> class fileStream
> {
> public:
>
> //default constructor
> fileStream();
>
> //constructor with filename
> fileStream(const string &fileName);
>
> //destructor
> ~fileStream() {if (inFile.is_open()) inFile.close( );}
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The marked part is redundant, ifstream's dtor will take care of this.
However, I'd like to add a few things to what was said about these ctors.
You should declare all three of default ctor, copy ctor assignment
operator. If you don't, the compiler will generate default
implementations. In this case, it can't create operator= and the cctor,
because ifstream is not copyable, but this is a general rule. Also, you
should make them private, so they are not accidentally invoked. So, your
class looks like this:
class file
{
// not default-constructible
file();
// not copyable
file( file const&);
// not assignable
file& operator=( file const&);
public:
// construct with a filename
explicit file( std::string const& filename);
~file();
};
Two things here:
1. Remember that fields in a class are by default private, so only from
inside the class or friend code you could accidentally compile code that
uses these forbidden parts.
2. The 'explicit' should be prefixed to all one-argument ctors that should
not be invoked implicitly.
Note that these things run along the guideline to create an error as early
as possible:
- Prefer compiler errors to linker errors.
- Prefer linker errors to runtime errors.
- Prefer runtime assertions to undefined behaviour.
The private/unaccessible parts should not be implemented, so even if you
manage to compile code that uses these, you would at least get a linker
error.
Uli
--
FAQ: http://ma.rtij.nl/acllc-c++.FAQ.html
-
Re: Newbie: Cancelling the creation of a class object
"TreatmentPlant" <NoEmailThanks@DieSpammers.com> wrote in message
news:454424d4$0$18093$5a62ac22@per-qv1-newsreader-01.iinet.net.au...
> Is it possible to cancel or prevent the creation of a class object?
>
> I have a fileClass which has a default and non-default constructor
> (fileName provided as argument). If no fileName is provided or the
> provided fileName does not exist or cannot be opened for reading, I would
> like to cancel the creation of the class object.
>
> Is this possible, if so, how?
>
> (I would prefer, if possible to do the test at the class level, rather
> than test for a fileName in the program proper and only if successful
> create the object.)
>
>
> class fileStream
> {
> public:
>
> //default constructor
> fileStream();
>
> //constructor with filename
> fileStream(const string &fileName);
>
> //destructor
> ~fileStream() {if (inFile.is_open()) inFile.close( );}
>
> private:
>
> //the input file stream for reading from the file
> ifstream inFile;
> };
>
>
> //--------------------------------------------------------
> //default constructor
> //--------------------------------------------------------
> fileStream::fileStream()
> {
> //how do I cancel the construction of an object?
> }
>
> //--------------------------------------------------------
> //non-default constructor, fileName provided
> //--------------------------------------------------------
> fileStream::fileStream(const string &fileName)
> {
> if (fileName!="")
> {
> try
> {
> //attempt to open the file
> inFile.open(fileName.c_str());
> }
> catch (...)
> {
> //how do I cancel the construction of an object?
>
> //if the file cannot be opened or not found
> cout << "\aERROR : \"" << fileName << "\" cannot be found or opened." <<
> endl;
> }
> }
> }
In addition to the others suggestions of throwing and exception, consider
using a factory to create the object. The factory can create the object,
then test it somehow (perhaps call object.is_good()) and if it's good return
a pointer to it, otherwise delete it and return NULL.
Similar Threads
-
By Application Development in forum c++
Replies: 4
Last Post: 11-13-2007, 11:07 AM
-
By Application Development in forum Python
Replies: 4
Last Post: 08-18-2007, 12:05 PM
-
By Application Development in forum DOTNET
Replies: 0
Last Post: 06-05-2007, 03:38 AM
-
By Application Development in forum DOTNET
Replies: 1
Last Post: 03-13-2006, 06:24 AM
-
By Application Development in forum CSharp
Replies: 1
Last Post: 02-16-2005, 08:43 AM