Velocity Reviews

Velocity Reviews (http://www.velocityreviews.com/forums/index.php)
-   C++ (http://www.velocityreviews.com/forums/f39-c.html)
-   -   weird output for equations... (http://www.velocityreviews.com/forums/t459101-weird-output-for-equations.html)

Blah 12-11-2006 02:30 AM

weird output for equations...
 
Hi, this is a small program to print out three lists of values. One is
a simple increment count the others are values from two equations. I've
run this without problems before but when I've put in the new equations
I sometimes get columns of -1.#IND. I think it might have something to
do with using a wrong type or not including some important library
file, but I'm not sure and google has been little help. Anyone know the
problem?

Thanks...



#include <iostream> // for std::cout
#include <fstream>
#include <iomanip>
using namespace std;
void choice();

double xnext, ynext, i;

double step = 0.0001;
double x = 10;
double r = 1.00;
double k = 5000.;
double d = .001;
double y = 5.;
double p = .5;
double a = .001;
double count = 0;
double count2 = 0;
double count3 = 0;



int main()
{
int vart;

cout << "1. x=" << x << endl << "2. r=" << r << endl << "3. k=" << k
<< endl << "4. d=" << d << endl;
cout << "5. y=" << y << endl << "6. p=" << p << endl << "7. a=" << a
<< endl<< "8. step=" << step << endl;
cout << "Do you want to change something? 1= yes 2 = no" << endl;
cin >> vart;


if (vart == 1)
{
while (vart == 1)
{
choice();
cout << "1. x=" << x << endl << "2. r=" << r << endl << "3. k=" << k
<< endl << "4. d=" << d << endl;
cout << "5. y=" << y << endl << "6. p=" << p << endl << "7. a=" << a
<< endl<< "8. step=" << step << endl;
cout << "Do you want to change something?" << endl;
cin >> vart;

}
}


ofstream dataout;

dataout.open("res.dat", ios::out);

for (i = 1; i <= 500000; i++)
{
count = count + 1;
count2 = count2 + 1;
count3 = count3 + 1;


if (count2 == 1000)
{
cout << step*i << std::endl;
count2 = 0;

}

xnext = (r*x*(1-x/k))-(d*x)-(p*x*y);



ynext = (p*x*y)-(a*y);
x = xnext;
y = ynext;


if (count == 100)
{
dataout.precision(10);
dataout << i*step << " " << x << " " << y <<
std::endl;
count = 0;

}


}





dataout.close();
return 0;
}



void choice()
{
int choice;


cout<< "what do you wish to change?" << endl;
cin >> choice;

switch (choice)

{
case 1:
cin >> x;
break;
case 2:
cin >> r;
break;
case 3:
cin >> k;
break;
case 4:
cin >> d;
break;
case 5:
cin >> y;
break;
case 6:
cin >> p;
break;
case 7:
cin >> a;
break;
case 8:
cin >> step;
break;

default:
cout << "value of x unknown" << endl;
}
}


osmium 12-11-2006 02:59 AM

Re: weird output for equations...
 
"Blah" wrote:

> Hi, this is a small program to print out three lists of values. One is
> a simple increment count the others are values from two equations. I've
> run this without problems before but when I've put in the new equations
> I sometimes get columns of -1.#IND. I think it might have something to
> do with using a wrong type or not including some important library
> file, but I'm not sure and google has been little help. Anyone know the
> problem?


<snip>

> void choice()
> {
> int choice;


I have no idea what this program is supposed to do or what your problem is
but I have a strong distaste for using one word for two different things in
the same program.



eriwik@student.chalmers.se 12-11-2006 07:32 AM

Re: weird output for equations...
 
On Dec 11, 3:30 am, "Blah" <cidste...@yahoo.com> wrote:
> Hi, this is a small program to print out three lists of values. One is
> a simple increment count the others are values from two equations. I've
> run this without problems before but when I've put in the new equations
> I sometimes get columns of -1.#IND. I think it might have something to
> do with using a wrong type or not including some important library
> file, but I'm not sure and google has been little help. Anyone know the
> problem?


Haven't lookt at your code but are you sure you have initialized all
variables correctly?

--
Erik Wikström


Ron Natalie 12-11-2006 12:26 PM

Re: weird output for equations...
 
Blah wrote:

>
> int main()
> {
> int vart;
>
> cout << "1. x=" << x << endl << "2. r=" << r << endl << "3. k=" << k
> << endl << "4. d=" << d << endl;


semicolons and newlines cost you nothing and make your code more
readable.
>
> if (vart == 1)
> {
> while (vart == 1)

The if here is entirely redundant with the while.

> {
> choice();
> cout << "1. x=" << x << endl << "2. r=" << r << endl << "3. k=" << k
> << endl << "4. d=" << d << endl;
> cout << "5. y=" << y << endl << "6. p=" << p << endl << "7. a=" << a
> << endl<< "8. step=" << step << endl;
> cout << "Do you want to change something?" << endl;
> cin >> vart;
>
> }
> }

This apepars to be largely a repeat of thestuff at the beginning of
main. You know you can do soething like:
while(true) {
// all those couts...
cin >> vart;
if(vart !- 1) break;
choice();
}

>
> xnext = (r*x*(1-x/k))-(d*x)-(p*x*y);
>
>

Most likely you're abusing the floating point math. What is
the value of k for the failing case? etc...

BobR 12-11-2006 08:39 PM

Re: weird output for equations...
 

Ron Natalie wrote in message ...
>Blah wrote:
>
>> int main(){
>> cin >> vart;
>>

>This apepars to be largely a repeat of thestuff at the beginning of
>main. You know you can do soething like:
> while(true) {
> // all those couts...
> cin >> vart;

//> if(vart !- 1) break;
if( vart != 1 ) break;

> choice();
> }


Add for OP:

ofstream dataout("res.dat");
dataout.setf( std::ios_base::fixed ); // for test
dataout.precision( 400 ); // for test

>
>>
>> xnext = (r*x*(1-x/k))-(d*x)-(p*x*y);


dataout<< xnext <<std::endl;

>>
>>

>Most likely you're abusing the floating point math. What is
>the value of k for the failing case? etc...


I'll bet you (the OP) are running on an windows machine. Very big and very
small double numbers hit a wall at the OS level (streams). Try it on a
GNU/Linux machine.

Try this:
// #include <limits> <iostream> <iomanip>
{ // main or function.
using std::cout // for NG post
std::string DblMax("");
{
std::ostringstream out;
out.setf(std::ios_base::fixed);
out.precision(400);
double tmp( std::numeric_limits<double>::max() / 1.0e+276);
out<<(tmp);
DblMax=out.str();
}
cout <<"DblMax=out.str() = "<<DblMax<<endl;
DblMax = "";
{
std::ostringstream out;
out.setf(std::ios_base::fixed);
out.precision(400);
double tmp( std::numeric_limits<double>::max() / 1.0e+275); // note
change
out<<(tmp);
DblMax=out.str();
}
cout <<"DblMax=out.str() = "<<DblMax<<endl;
} // end


Your findings?

--
Bob R
POVrookie



Blah 12-14-2006 08:17 AM

Re: weird output for equations...
 

Ron Natalie wrote:
> Blah wrote:
>
> >
> > int main()
> > {
> > int vart;
> >
> > cout << "1. x=" << x << endl << "2. r=" << r << endl << "3. k=" << k
> > << endl << "4. d=" << d << endl;

>
> semicolons and newlines cost you nothing and make your code more
> readable.
> >
> > if (vart == 1)
> > {
> > while (vart == 1)

> The if here is entirely redundant with the while.
>
> > {
> > choice();
> > cout << "1. x=" << x << endl << "2. r=" << r << endl << "3. k=" << k
> > << endl << "4. d=" << d << endl;
> > cout << "5. y=" << y << endl << "6. p=" << p << endl << "7. a=" << a
> > << endl<< "8. step=" << step << endl;
> > cout << "Do you want to change something?" << endl;
> > cin >> vart;
> >
> > }
> > }

> This apepars to be largely a repeat of thestuff at the beginning of
> main. You know you can do soething like:
> while(true) {
> // all those couts...
> cin >> vart;
> if(vart !- 1) break;
> choice();
> }
>
> >
> > xnext = (r*x*(1-x/k))-(d*x)-(p*x*y);
> >
> >

> Most likely you're abusing the floating point math. What is
> the value of k for the failing case? etc...


k fails at 5000 which is the case here...although reducing it to 10
doesn't help. I've only been able to get it to work a few times by
playing with the variables. For example, changing x and y to .5 will
prevent the #INDs. I don't know the magic limit where it will change
though. The lower the starting values of the variables which increase
the output values (especially r) the more likely it will not give
-1.#IND lists (but the values for both equations quickly go to zero
which is not what I want). It would seem getting output values that are
too high or too low might be the problem but wouldn't setting precision
take care of this? Is there some library files I can include to fix
this? Or maybe a more appropriate type?


Blah 12-14-2006 08:22 AM

Re: weird output for equations...
 

> I'll bet you (the OP) are running on an windows machine. Very big and very
> small double numbers hit a wall at the OS level (streams). Try it on a
> GNU/Linux machine.
>
> Try this:
> // #include <limits> <iostream> <iomanip>
> { // main or function.
> using std::cout // for NG post
> std::string DblMax("");
> {
> std::ostringstream out;
> out.setf(std::ios_base::fixed);
> out.precision(400);
> double tmp( std::numeric_limits<double>::max() / 1.0e+276);
> out<<(tmp);
> DblMax=out.str();
> }
> cout <<"DblMax=out.str() = "<<DblMax<<endl;
> DblMax = "";
> {
> std::ostringstream out;
> out.setf(std::ios_base::fixed);
> out.precision(400);
> double tmp( std::numeric_limits<double>::max() / 1.0e+275); // note
> change
> out<<(tmp);
> DblMax=out.str();
> }
> cout <<"DblMax=out.str() = "<<DblMax<<endl;
> } // end
>
>
> Your findings?
>
> --
> Bob R
> POVrookie


I'm sorry, I'm inexperienced so I could not get the code to work. Did
you intend it to be run as a stand alone test? I don't have a Linux box
at the moment but I guess I can get access to one soon.


BobR 12-14-2006 09:03 PM

Re: weird output for equations...
 

Blah wrote in message ...
>
>Ron Natalie wrote:
>>
>> Most likely you're abusing the floating point math. What is
>> the value of k for the failing case? etc...

>
>k fails at 5000 which is the case here...although reducing it to 10
>doesn't help. I've only been able to get it to work a few times by
>playing with the variables. For example, changing x and y to .5 will
>prevent the #INDs. I don't know the magic limit where it will change
>though. The lower the starting values of the variables which increase
>the output values (especially r) the more likely it will not give
>-1.#IND lists (but the values for both equations quickly go to zero
>which is not what I want). It would seem getting output values that are
>too high or too low might be the problem but wouldn't setting precision
>take care of this? Is there some library files I can include to fix
>this? Or maybe a more appropriate type?


The -1.#IND is a windows thing. On GNU it most likely will output the full
number (several lines of it, many zeros).
Only thing to do is test against the numeric limits[1] and output 'fixed' or
'scientific' depending.

There are some 3rd party large-number libraries around.

[1] /*
struct numeric_limits<double>{
static double min();
static double max();
static double epsilon();
static double round_error();
static double infinity();
static double quiet_NaN();
static double signaling_NaN();
static double denorm_min();
};
*/


This is butt-ugly, but, I put this together to see output on a windows
machine:

#include <iostream>
#include <ostream> // std::endl
#include <sstream> // I forgot this in other post
#include <string> // ..and this <~G>
#include <limits>
#include <iomanip>

int main(){
{ // positive number only
using std::cout; // for NG posts.
std::stringstream temp;
temp.precision(400);
temp << std::numeric_limits<double>::max();
temp.setf(std::ios_base::fixed); // no effect here, could remove
std::string to;
temp >> to;
size_t dpoint( to.find('.') );
size_t de( to.find('e') ); // could be 'E'
std::string whole( to.substr(0, dpoint) );
std::string frac( to.substr( dpoint+1, (de - dpoint)-1));
std::string expon( to.substr( de+2 ) ); // skip 'e+'
int sz;
{ std::istringstream sis( expon.c_str() ); sis >> sz; }
sz -= frac.size();
std::string toadd( sz, '0' );
std::string final = whole + frac + toadd + ".000";
cout <<" final = "<<final<<std::endl;
cout <<" final.size() = "<<final.size()<<std::endl;
cout<<std::endl;
}
return 0;
} // main()

// temp >> string to = 1.7976931348623157e+308
// note: line breaks inserted for NG post.
// final = 1797693134862315700000000000000000000000000000000
00000000000000000000000000000000000000000000000000 0000000
00000000000000000000000000000000000000000000000000 0000000
00000000000000000000000000000000000000000000000000 0000000
00000000000000000000000000000000000000000000000000 0000000
00000000000000000000000000000000.000
// final.size() = 313

I wouldn't trust the accuracy of that, it's just for exhibit.

On a GNU/Linux machine, all you'd do is:

{
using std::cout; // for NG posts.
cout.precision( 400 );
cout.setf( std::ios_base::fixed );
cout << std::numeric_limits<double>::max() <<std::endl;
}

Try that on your windows machine. Work?
(if 'yes', what win version? what (date) 'msvcrt.dll'? (where the bug
is[2])).

[2] - I think the critical buffer may be size 255 (where 310+ is needed).
[ experts, feel free to correct me. ]
--
Bob R
POVrookie



Blah 12-17-2006 09:36 AM

Re: weird output for equations...
 

>
> There are some 3rd party large-number libraries around.
>
> [1] /*
> struct numeric_limits<double>{
> static double min();
> static double max();
> static double epsilon();
> static double round_error();
> static double infinity();
> static double quiet_NaN();
> static double signaling_NaN();
> static double denorm_min();
> };
> */
>
>
> This is butt-ugly, but, I put this together to see output on a windows
> machine:
>
> #include <iostream>
> #include <ostream> // std::endl
> #include <sstream> // I forgot this in other post
> #include <string> // ..and this <~G>
> #include <limits>
> #include <iomanip>
>
> int main(){
> { // positive number only
> using std::cout; // for NG posts.
> std::stringstream temp;
> temp.precision(400);
> temp << std::numeric_limits<double>::max();
> temp.setf(std::ios_base::fixed); // no effect here, could remove
> std::string to;
> temp >> to;
> size_t dpoint( to.find('.') );
> size_t de( to.find('e') ); // could be 'E'
> std::string whole( to.substr(0, dpoint) );
> std::string frac( to.substr( dpoint+1, (de - dpoint)-1));
> std::string expon( to.substr( de+2 ) ); // skip 'e+'
> int sz;
> { std::istringstream sis( expon.c_str() ); sis >> sz; }
> sz -= frac.size();
> std::string toadd( sz, '0' );
> std::string final = whole + frac + toadd + ".000";
> cout <<" final = "<<final<<std::endl;
> cout <<" final.size() = "<<final.size()<<std::endl;
> cout<<std::endl;
> }
> return 0;
> } // main()
>
> // temp >> string to = 1.7976931348623157e+308
> // note: line breaks inserted for NG post.
> // final = 1797693134862315700000000000000000000000000000000
> 00000000000000000000000000000000000000000000000000 0000000
> 00000000000000000000000000000000000000000000000000 0000000
> 00000000000000000000000000000000000000000000000000 0000000
> 00000000000000000000000000000000000000000000000000 0000000
> 00000000000000000000000000000000.000
> // final.size() = 313
>
> I wouldn't trust the accuracy of that, it's just for exhibit.
>



> Try that on your windows machine. Work?
> (if 'yes', what win version? what (date) 'msvcrt.dll'? (where the bug
> is[2])).
>
> [2] - I think the critical buffer may be size 255 (where 310+ is needed).
> [ experts, feel free to correct me. ]
> --
> Bob R
> POVrookie



I tried the above code but although it built correctly, running gave
the "this application has asked runtime to terminate in in an unusual
way"



All times are GMT. The time now is 10:50 AM.

Powered by vBulletin®. Copyright ©2000 - 2014, vBulletin Solutions, Inc.
SEO by vBSEO ©2010, Crawlability, Inc.