|
1. Today's stupid question...
|
|
Fri Feb 16, 2007 [11:08 AM]
|
Pewter
Email not supplied
member since: Dec 12, 2001
|
Reply
|
|
Getting excited... spent until after midnight bringing 5 year old code slowly back online while rewriting it to reflect everything new I've learned in the last 5 years...
But as much as I google and search the web, I am hard pressed to find examples of some simple things. So I ask your patience in providing me with simple answers that once I have coded them once, I can duplicate ad nauseum...
First area of concern has to do with passing filestreams to functions. I am hampered by the fact that up until now, my code has never passed filestreams (they were opened and closed within the class/function that used them). I also have the problem that up until now, my files have always been text only...
Current code...
void MUDclass::LoadMUD(void) //loads MUD from file { ifstream inMUDfilestream; string MUDfilename= "c://MUD.sav";
inMUDfilestream.open(MUDfilename.c_str(), ios::in);****1**** if(inMUDfilestream) { //file opened timeclassaccessptr -> LoadTime(****2****): ...and so on for each class needing loaded } else { //file does not exist cout << "Error in opening MUD file.\n\r"; //LoadTime would not be called and time would default to initialized values } inMUDfilestream.close(); return; } *******************
And the SaveMUD would undergo the reverse...
void MUDclass::SaveMUD(void) //saves MUD to file { ofstream inMUDfilestream; string MUDfilename= "c://MUD.sav";
outMUDfilestream.open(MUDfilename.c_str(), ios::in);****3**** if(outMUDfilestream) { //file opened timeclassaccessptr -> SaveTime(****4****); ...and so on for each class needing saved } else { //file does not exist cout << "Unable to save MUD.\n\r"; //SaveTime would not be called since there is no place to store the values. } inMUDfilestream.close(); return; } ******************* In timeclass.h
void LoadTime(****5****)
and
void SaveTime(****6****)
******************* And finally in timeclass.cpp
void timeclass::LoadTime(****7****) { ****8****
****9**** >> Minutes; ****9**** >> Hours; and so on... }
and
void timeclass::SaveTime(****10****) { ****11****
****12**** << Minutes; ****12**** << Hours; and so on... }
and so the questions... ****1**** I want the file to be able to contain a mixture of strings, integers, and booleans. How do I modify this to accomplish that?
****2**** What goes here based on the example code? This is really the issue that I cannot find anything online or in my references to describe to me. What about use of const and static?
****3**** Same issue as in number 1 as I want the file to be able to store a mixture of strings, integers, and booleans. How do I modify this to accomplish that?
****4**** Similar to number 2, what goes here based on the example code?
****5**** and ****6**** What do I specify in the header based on the sample code? What about use of const and static?
****7**** What goes here?
****8**** I assume that what I have in number 7 impacts whether I need to declare anything here or not. How would you do it?
****9**** Assuming that this is something contained in number 7 or possibly number 8.
****10****, ****11****, and ****12**** I am assuming these are nearly identical in nature to 7, 8, and 9. Correct?
Finally, I have tried to code examples and get obscure error messages which have no further help files available. So please provide me this first example and I can clone it from here on out.
Thanks in advance for your time and answers, Pewter
|
|
|
|
|
2. RE: Today's stupid question...
|
|
Sat Feb 17, 2007 [5:17 AM]
|
Scarab_XXX
Email not supplied
member since: Mar 27, 2006
|
In Reply To
Reply
|
|
|
|
Scarab,
Fledgling Curmudgeon
|
|
3. RE: Today's stupid question...
|
|
Mon Feb 19, 2007 [7:59 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Time for another one...
When I first started coding (5 or 6 years ago) someone here put me on to stringoperations.h. I believe they sent me their source code for it, which calls out <sstream>. I also remember going through the search for <sstream> as Borland C++ 5.02 does not contain it. Could someone please provide me a link where I can get the <sstream> files to include in my library? Web searches I do tend to turn up tutorials/code on using <sstream> but no actual files.
Thanks in advance, Pewter
|
|
|
|
|
4. RE: Today's stupid question...
|
|
Mon Feb 19, 2007 [9:11 AM]
|
Tyche
Email not supplied
member since: Apr 4, 2000
|
In Reply To
Reply
|
I'm guessing that BC 5.02 contains an obsolete STL. The only alternative STL that I know of that might work with it would be STLPort. But why would you use that old compiler when you could update your compiler to the less buggy and free Borland 5.5 C++ compiler, which comes with a more current version of the RogueWave STL, and works even better with the STLPort STL.
|
|
|
|
|
5. RE: Today's stupid question...
|
|
Mon Feb 19, 2007 [10:33 AM]
|
Pewter
Email not supplied
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
The Borland site comes up with a 404 error... maybe they don't download it any more...
Also, the 5.5 does not have the development environment but forces command line control... I am having enough trouble mastering what I have... *smile*
|
|
|
|
|
6. RE: Today's stupid question...
|
|
Tue Feb 20, 2007 [4:49 AM]
|
Kastagaar
Email not supplied
member since: Jul 29, 1999
|
In Reply To
Reply
|
Aside from your problems getting a decent implementation of the STL, here's a small sample program that shows one way of writing in and out of files "the C++ way". #include <iostream>
#include <fstream>
using namespace std;
class point
{
public :
point(int x, int y)
: x_(x), y_(y)
{}
int get_x() const { return x_; }
void set_x(int x) { x_ = x; }
int get_y() const { return y_; }
void set_y(int y) { y_ = y; }
friend ostream& operator<<(ostream&, point const&);
friend istream& operator>>(istream&, point &);
private :
int x_;
int y_;
};
ostream& operator<<(ostream& out, point const& pt)
{
out << pt.x_ << " " << pt.y_;
return out;
}
istream& operator>>(istream& in, point &pt)
{
in >> pt.x_ >> pt.y_;
return in;
}
int main()
{
{
point pt(4, 9);
ofstream fout("mytest.pt");
fout << pt;
}
{
point pt(76, 289);
ifstream fin("mytest.pt");
fin >> pt;
cout << "point(" << pt.get_x() << ", " << pt.get_y() << ")" << endl;
// Should be "point(4, 9)" when you run it.
}
}
In any case, I would advise buying the book "The C++ Standard Library" (Josuttis), which is an excellent, readable book that documents all sorts of stuff that Every C++ Programmer Should Know. It's worth its weight in gold. Really.
|
|
|
There are two ways of constructing software: to make it so simple that there are obviously no errors, and to make it so complex that there are no obvious errors.
|
|
7. RE: Today's stupid question...
|
|
Tue Feb 20, 2007 [7:12 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Would some nice person that happened to keep their free Borland C++ 5.5 download please send me the sstream files from it via email? I spent three hours online chasing the files without any luck last night. Needless to say, getting very frustrated because I should be coding, not hassling with tools...
Thanks in advance, Pewter
|
|
|
|
|
8. RE: Today's stupid question...
|
|
Tue Feb 20, 2007 [8:54 AM]
|
CheeseG
Email not supplied
member since: Mar 24, 2006
|
In Reply To
Reply
|
|
sstream is part of the standard C++ library. It's not advisable to try to get just that part of it piecemeal.
You need to get a more recent version of libstdc++, in your case that is probably accomplished most easily by upgrading to a more current compiler.
|
|
|
|
|
9. RE: Today's stupid question...
|
|
Tue Feb 20, 2007 [8:54 AM]
|
Razzer_9
Email not supplied
member since: Mar 5, 2001
|
In Reply To
Reply
|
|
Would some nice person that happened to keep their free Borland C++ 5.5 download please send me the sstream files from it via email? I spent three hours online chasing the files without any luck last night. Needless to say, getting very frustrated because I should be coding, not hassling with tools...
Drop Borland and get a good, free system. Look at MinGW or even Cygwin. You can get the g++ compiler, which is far superior to the free one Borland gives you.
|
|
|
|
|
10. RE: Today's stupid question...
|
|
Tue Feb 20, 2007 [9:21 AM]
|
Kastagaar
Email not supplied
member since: Jul 29, 1999
|
In Reply To
Reply
|
|
> Drop Borland and get a good, free system. Look at MinGW or > even Cygwin. You can get the g++ compiler, which is far > superior to the free one Borland gives you.
I'll admit that Borland has a nice IDE, but Cygwin is also what I use for my home-grown code, and jEdit is my editor.
|
|
|
There are two ways of constructing software: to make it so simple that there are obviously no errors, and to make it so complex that there are no obvious errors.
|
|
11. RE: Today's stupid question...
|
|
Tue Feb 20, 2007 [9:53 AM]
|
Tyche
Email not supplied
member since: Apr 4, 2000
|
In Reply To
Reply
|
|
|
|
|
|
12. RE: Today's stupid question...
|
|
Wed Feb 21, 2007 [8:13 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Hmmm... light bulb (a very small one) may have just gone off...
Looking at...
friend ostream& operator<<(ostream&, point const&); friend istream& operator>>(istream&, point &);
In general, do all of the standard classes like int, bool, float, etc. have this defined within the class?
In other words, can I do...
*pseudocode* int Date; char* Month; string Title; bool Today;
ofstream fout; fout << Date; fout << Month: fout << Title; fout << Today;
ifstream fin; fin >> Date; fin >> Month; fin >> Title; fin >> Today;
...and end up with all the right values? Are there any of the common classes for which this is not true?
|
|
|
|
|
13. sstream.h and sstream.cpp for Borland 5.02
|
|
Wed Feb 21, 2007 [8:25 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Been there before...
The Borland/Codegear site no longer appears to support the download of 5.5...
I get logged into the site and get unrecognized product errors when I click to download...
I believe I actually got the sstream file for Borland 5.2 from the same person that recommended stringoperations.h to me. No idea who that was since it was 6 years ago. But it seemed to work with the rest of the library from 5.02.
While I appreciate all of the recommendations to get a real compiler, I am comfortable with the one I have. Somewhat an "old dog, new tricks" issue but also the fact that I am struggling along at the limits of my knowledge in C++ and so just coding is enough of a struggle without confusing things with trying to learn a new environment.
Please realize I tried Borland C++ Builder 4.0 at the time and got rid of it because it interferred with me just trying to compile and link my simple programs. As funny as it may sound, it was hard for me to even do the "Hello World" program in that environment.
Would all of you please look in your archives and see if any of you have the Borland 5.2 C++ compiler and could extract and send me the sstream related files? It would save me having to rewrite a lot of code to use the old character based string functions.
Thanks, Pewter
|
|
|
|
|
14. sstream from 5.5 does not work with 5.02
|
|
Wed Feb 21, 2007 [8:28 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Managed to get 5.5 from a friend who hadn't thrown it away yet...
Introduction of the sstream files from 5.5 into the 5.02 environment result in a bunch of additional errors so this is obviously not the path I took 5 years ago. Now looking for Borland 5.2...
|
|
|
|
|
15. RE: Today's stupid question...
|
|
Wed Feb 21, 2007 [7:17 PM]
|
Scarab_XXX
Email not supplied
member since: Mar 27, 2006
|
In Reply To
Reply
|
In general, do all of the standard classes like int, bool, float, etc. have this defined within the class?
[pedantic] Those are primitive types, not classes, so, no, this is not defined within the class [/pedantic] In other words, can I do... <snip>
Yes, despite my pedantic note above, this will work. Have you check out this yet? http://www.cplusplus.com/doc/tutorial/files.htmlHow about this? http://www.cplusplus.com/doc/tutorial/basic_io.html
|
|
|
Scarab,
Fledgling Curmudgeon
|
|
16. RE: Today's stupid question...
|
|
Thu Feb 22, 2007 [4:00 AM]
|
Kastagaar
Email not supplied
member since: Jul 29, 1999
|
In Reply To
Reply
|
Pewter > Hmmm... light bulb (a very small one) may have just gone > off... > > Looking at... > > friend ostream& operator<<(ostream&, point const&); > friend istream& operator>>(istream&, point &); > > In general, do all of the standard classes like int, bool, > float, etc. have this defined within the class? Yes, no, almost, not quite. Note the "friend". This states that "Elsewhere, external to the class, there is this function that can have access to our private parts*" The operator itself is not part of the class; it is a free function. (Aside: If your class is designed such that, to output it, you don't need to access the private member variables, then you don't need these friend declarations. However, the operators are a part of the logical interface of the class, so it doesn't really hurt.) So the literal answer to your question is "no." for this reason (in addition to the primitive types of bool, int, etc., not being classes) However, overloads for operators << and >> for primitive types do exist. There are a couple of caveats, though, mostly to do with delimiters. If you output (<<) two integers in a row, (say, 42 and 24), you'll get one big integer (4224) read back in. Note in the code above that operator<< has a space output between the fields. The second caveat is in std::string, which also has operators << and >> overloaded. Its default delimiter is a space. Thus, if you have the text "Hello, World", and you read into a string, it'll contain the text "Hello,". This is fairly trivial to get around. For fun, I knocked together a class demonstrating this: #include <iostream>
#include <fstream>
#include <string>
using namespace std;
class terminated_string
{
public :
terminated_string(string& ref, char terminator)
: ref_(ref), terminator_(terminator)
{
}
friend ostream& operator<<(ostream&, terminated_string const&);
friend istream& operator>>(istream&, terminated_string const&);
private :
string& ref_;
char terminator_;
};
ostream &operator<<(ostream& out, terminated_string const& str)
{
out << str.ref_;
out << str.terminator_;
}
// Usually, operator>> takes a non-const rhs. However, because
// terminated_string is a kind of smart reference, this is a special case.
// It also allows us to bind to the temporaries below.
istream &operator>>(istream& in, terminated_string const& str)
{
while (in)
{
int ich = in.get();
if (ich >= 0)
{
char ch = char(ich);
if (ch == str.terminator_)
{
return in;
}
else
{
str.ref_.push_back(ch);
}
}
}
}
int main()
{
{
ofstream out("mytest.tst");
out << "hallelujah! All be praised! Yarr!" << endl;
}
{
ifstream in("mytest.tst");
string str1;
string str2;
string str3;
in >> terminated_string(str1, '!')
>> terminated_string(str2, 's')
>> terminated_string(str3, '\n');
cout << str1 << "\n" << str2 << "\n" << str3 << endl;
}
}
HTH. *A friend is someone who can access your privates, you see.
|
|
|
There are two ways of constructing software: to make it so simple that there are obviously no errors, and to make it so complex that there are no obvious errors.
|
|
17. RE: Today's stupid question...
|
|
Thu Feb 22, 2007 [7:14 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Thanks for the insight...
Actually the light bulb was going off for the overload of the << and >> for istream and ostream. I am assuming that s sstream does a similar overloading?
While it may not seem like it, I actually read and reread the manuals for two courses, the first on C and the second on C++ before starting into all of this. I also coded my own hostsocket using tutorials out on the web and winsock back five years ago. Some of my original code that predates my introduction to stringoperations.h (which I believe someone here put me onto) reads character by character to the EOF to input text into a char*. I also have code that saves and loads text for passwords and users names. So generally, if there is a good example of what I need to be had, I can clone it and have already done so.
My current problem is looking for a workaround to sstream unless someone with an old Borland 5.2 or so sends it to me. The functions from stringoperations.h/sstream that I used extensively were << and >> to do things like building rootdirectory << subdirectory << filename into a file to be opened for saving to or loading from.
I had a major success last night. I stumbled onto a disk that had all of the text files for my help commands, rules, philosophy, as well as a couple of area description files, so I am celebrating being saved a couple weeks of work recreating those. Now if I can find an sstream workaround or patch, that will save me a hundred or so hours of recoding things back to char strings and string catonation(sp?) functions.
But thanks for your help and the example and especially for your patience....
Pewter
|
|
|
|
|
18. RE: Today's stupid question...
|
|
Thu Feb 22, 2007 [7:18 AM]
|
Kastagaar
Email not supplied
member since: Jul 29, 1999
|
In Reply To
Reply
|
Yes, std::ostringstream and std::istringstream in the <sstream> header do all the << and >> stuff. For example, what must be one of the most common functions to get written using string streams is ToString: template <class T>
std::string ToString(T const &t)
{
std::stringstream sstr;
sstr << t;
return sstr.str();
}
|
|
|
There are two ways of constructing software: to make it so simple that there are obviously no errors, and to make it so complex that there are no obvious errors.
|
|
19. RE: Today's stupid question...
|
|
Thu Feb 22, 2007 [7:49 AM]
|
Pewter
pewtermug@yahoo.com
member since: Dec 12, 2001
|
In Reply To
Reply
|
|
Scarab,
Yeh, I caught the mistake after I hit approve. Not having had formal training my terminology will often go astray. I am glad you were able to figure out what I was actually asking.
cin and cout are "idiot-proofed" and so reading about them has not given me a good answer for my current quandry. You can apparently shove about any standard type into cout and it gets spit to the screen. It appears that cout could be "casting" (my word) everything into strings and dealing with strings. And so the only type dealt with in the underlying functionality would be strings or even char*'s. True? So when I talk about ofstreams instead, am I dealing with underlying character strings or binary streams or what?
You can also apparently enter any standard type into cin and it gets stored into the program as the proper type. Is the underlying mechanism a "string to whatevertype"? Or is it a "cast"? Or is it a binary operation where the stream knows how many bits long a certain type is and grabs only that number of bits? Or are there separators inserted into the streams as they are saved that are removed and they are loaded?
Forgive me but I assume these are things that people with formal training have discussed in class. Unfortunately the examples and tutorials online seem to be very simple and don't delve into the underlying details that really give you a solid understanding of the mechanisms involved. It is this "second level of detail" with which I am struggling and asking your help in mastering...
But thanks for your help and for your patience, Pewter
|
|
|
|
|
20. RE: Today's stupid question...
|
|
Thu Feb 22, 2007 [8:40 PM]
|
Scarab_XXX
Email not supplied
member since: Mar 27, 2006
|
In Reply To
Reply
|
You can also apparently enter any standard type into cin and it gets stored into the program as the proper type. Is the underlying mechanism a "string to whatevertype"? Or is it a "cast"? Or is it a binary operation where the stream knows how many bits long a certain type is and grabs only that number of bits? Or are there separators inserted into the streams as they are saved that are removed and they are loaded?
Well, different operators (<< and >>) are different stories. For the output operator (<<) the concept is called Operator Overloading, which, given that operators are function calls with a different syntax, is the same as Function Overloading. Each call such as cout << "Exit."; is really an overloaded operator call. You can create similar, custom functions for your classes. See these resources: http://www.5trees.com/ref/overloading_mechanism.htmlhttp://www.parashift.com/c++-faq-lite/operator-overloading.html#faq-13.7The input operator(>>) is another story. As Kastagaar indicated, there are some potential pitfalls. Check out this tutorial as well: http://www.daniweb.com/tutorials/tutorial6542.html
|
|
|
Scarab,
Fledgling Curmudgeon
|
|
21. RE: Today's stupid question...
|
|
Thu Feb 22, 2007 [10:15 PM]
|
Tyche
Email not supplied
member since: Apr 4, 2000
|
In Reply To
Reply
|
|
My current problem is looking for a workaround to sstream unless someone with an old Borland 5.2 or so sends it to me.
I have the compiler and it never had sstream. Instead it has strstream which is an obsolete STL feature that sstream replaces. If you want an up to date STL for BC 5.02, then download, build and install STLPort (link provided earlier).
|
|
|
|
|
22. RE: Today's stupid question...
|
|
Fri Feb 23, 2007 [2:34 AM]
|
Kastagaar
Email not supplied
member since: Jul 29, 1999
|
In Reply To
Reply
|
> You can also apparently enter any standard type into cin and > it gets stored into the program as the proper type. Is the > underlying mechanism a "string to whatevertype"? Or is it a > "cast"? Or is it a binary operation where the stream knows > how many bits long a certain type is and grabs only that > number of bits? Or are there separators inserted into the > streams as they are saved that are removed and they are > loaded? None of the above. First, understand that: int x, y;
cout << x << " " << y << endl;
is shorthand for: int x, y;
operator<<(operator<<(operator<<(operator<<(cout, x), " "), y), endl);
operator<< is overloaded for each basic type. For example, looking through the headers in my Cygwin implementation, I can see that ostream has overloads for: char, char const*, long, unsigned long, bool, short, unsigned short, int, unsigned int, long long, unsigned long long, double, float, long double, and finally void const*. No casting or other trickery required. It's just function overloading, just like I did above.
|
|
|
There are two ways of constructing software: to make it so simple that there are obviously no errors, and to make it so complex that there are no obvious errors.
|
|