Assitance with C++ using pseudocode code (overflow/underflow) - c++

I'm barely into my 4th week of C++ in school and was looking to be guided in the right direction.
#include "std_lib_facilities_3.h"
class BadArea{};
int area(int length, int width){
if(length <= 0 || width <=0) throw BadArea();
return length * width;
}
double mysqrt(double x){
if(x < 0.0) error("mysqrt");
return 1.0; //dummy value for now, need to write code later
}
int main(){
try{
char length = 0;
char width = 0;
cout << "Enter length and width seperated by a space\n";
cin >> length;
cin >> width;
vector<double> v(10);
v[9] = 7.5;
cout << area(7, -10) << '\n';
cout << mysqrt(-2.0) << '\n';
return 0;
}
catch(BadArea){
cerr << "Exception: Bad area\n";
}
catch(exception& e){
cerr << "ExceptionZ: " << e.what() << '\n';
}
catch(...){
cerr << "Exception occurred\n";
}
}
And this is what the assignment is asking us;
//Check for overflow in the area function
result = length * width
if result is negative or result/length <> width, throw an exception
//Use 3 iterations of the Newton-Raphson method for mysqrt
if x is 0, result is 0 so return it
if x is 1, result is 1 so return it
otherwise,
result = (x^4 + 28x^3 + 70x^2 + 28x + 1)/(8*(1 + x)*(1 + 6x + x^2))
Change the main to have an infinite loop around the try/catch part; in the try
block ask for length and width; if cin fails then return, otherwise print
the area, and print mysqrt of the area. Name your program hw3pr2.cpp. (Recall
that cin will fail if you type something that is not a properly-formatted int,
e.g., the word "end".)
I understand how to read the code, but I'm having a hard time starting it, and sort of get confused with "scope" so far it compiles correctly but keeps on giving me Range Error: 10. does that mean I'm using the class area wrong?
could someone please point me in the right direction?
Thank you!

You're declaring a vector of 10 elements and trying to access the 11th item with v[10].
[EDIT] As others have pointed out, std::vector doesn't do bounds checking by default, but if "std_lib_facilities_3.h" is similar to this, then it defines its own range-checked vector class.
[EDIT2] So you've updated your code so that length and width must be both greater than 0 or an BadArea exception will be thrown, but you're always calling area(7, -10), so you'll always get the exception. I think you want to pass the length and width to the area function: cout << area(length, width) << '\n';

Related

Program only works with inclusion of (side effects free) cout statements?

So I've been working on problem 15 from the Project Euler's website , and my solution was working great up until I decided to remove the cout statements I was using for debugging while writing the code. My solution works by generating Pascal's Triangle in a 1D array and finding the element that corresponds to the number of paths in the NxN lattice specified by the user. Here is my program:
#include <iostream>
using namespace std;
//Returns sum of first n natural numbers
int sumOfNaturals(const int n)
{
int sum = 0;
for (int i = 0; i <= n; i++)
{
sum += i;
}
return sum;
}
void latticePascal(const int x, const int y, int &size)
{
int numRows = 0;
int sum = sumOfNaturals(x + y + 1);
numRows = x + y + 1;
//Create array of size (sum of first x + y + 1 natural numbers) to hold all elements in P's T
unsigned long long *pascalsTriangle = new unsigned long long[sum];
size = sum;
//Initialize all elements to 0
for (int i = 0; i < sum; i++)
{
pascalsTriangle[i] = 0;
}
//Initialize top of P's T to 1
pascalsTriangle[0] = 1;
cout << "row 1:\n" << "pascalsTriangle[0] = " << 1 << "\n\n"; // <--------------------------------------------------------------------------------
//Iterate once for each row of P's T that is going to be generated
for (int i = 1; i <= numRows; i++)
{
int counter = 0;
//Initialize end of current row of P's T to 1
pascalsTriangle[sumOfNaturals(i + 1) - 1] = 1;
cout << "row " << i + 1 << endl; // <--------------------------------------------------------------------------------------------------------
//Iterate once for each element of current row of P's T
for (int j = sumOfNaturals(i); j < sumOfNaturals(i + 1); j++)
{
//Current element of P's T is not one of the row's ending 1s
if (j != sumOfNaturals(i) && j != (sumOfNaturals(i + 1)) - 1)
{
pascalsTriangle[j] = pascalsTriangle[sumOfNaturals(i - 1) + counter] + pascalsTriangle[sumOfNaturals(i - 1) + counter + 1];
cout << "pascalsTriangle[" << j << "] = " << pascalsTriangle[j] << '\n'; // <--------------------------------------------------------
counter++;
}
//Current element of P's T is one of the row's ending 1s
else
{
pascalsTriangle[j] = 1;
cout << "pascalsTriangle[" << j << "] = " << pascalsTriangle[j] << '\n'; // <---------------------------------------------------------
}
}
cout << endl;
}
cout << "Number of SE paths in a " << x << "x" << y << " lattice: " << pascalsTriangle[sumOfNaturals(x + y) + (((sumOfNaturals(x + y + 1) - 1) - sumOfNaturals(x + y)) / 2)] << endl;
delete[] pascalsTriangle;
return;
}
int main()
{
int size = 0, dim1 = 0, dim2 = 0;
cout << "Enter dimension 1 for lattice grid: ";
cin >> dim1;
cout << "Enter dimension 2 for lattice grid: ";
cin >> dim2;
latticePascal(dim1, dim2, size);
return 0;
}
The cout statements that seem to be saving my program are marked with commented arrows. It seems to work as long as any of these lines are included. If all of these statements are removed, then the program will print: "Number of SE paths in a " and then hang for a couple of seconds before terminating without printing the answer. I want this program to be as clean as possible and to simply output the answer without having to print the entire contents of the triangle, so it is not working as intended in its current state.
There's a good chance that either the expression to calculate the array index or the one to calculate the array size for allocation causes undefined behaviour, for example, a stack overflow.
Because the visibility of this undefined behaviour to you is not defined the program can work as you intended or it can do something else - which could explain why it works with one compiler but not another.
You could use a vector with vector::resize() and vector::at() instead of an array with new and [] to get some improved information in the case that the program aborts before writing or flushing all of its output due to an invalid memory access.
If the problem is due to an invalid index being used then vector::at() will raise an exception which you won't catch and many debuggers will stop when they find this pair of factors together and they'll help you to inspect the point in the program where the problem occurred and key facts like which index you were trying to access and the contents of the variables.
They'll typically show you more "stack frames" than you expect but some are internal details of how the system manages uncaught exceptions and you should expect that the debugger helps you to find the stack frame relevant to your problem evolving so you can inspect the context of that one.
Your program works well with g++ on Linux:
$ g++ -o main pascal.cpp
$ ./main
Enter dimension 1 for lattice grid: 3
Enter dimension 2 for lattice grid: 4
Number of SE paths in a 3x4 lattice: 35
There's got to be something else since your cout statements have no side effects.
Here's an idea on how to debug this: open 2 visual studio instances, one will have the version without the cout statements, and the other one will have the version with them. Simply do a step by step debug to find the first difference between them. My guess is that you will realize that the cout statements have nothing to do with the error.

how to convert an for loop to while loop c++

I'm trying to convert a for loop to while loop in c++ and do some checking for duplicates in a random number generator for generating lotto numbers so far all the stuff i'm trying seems to make the compiler very unhappy and I could really use a few pointers. It's the for loop in the Harray() function that feeds the Balls[] array
that i want to convert to a while loop.
#include<iostream>
#include<cstdlib> // to call rand and srand.
#include<ctime> // to make rand a bit more random with srand(time(0)) as first call.
#include<iomanip> // to manipulate the output with leading 0 where neccesary.
using namespace std;
// Hrand() function create and return a random number.
int Hrand()
{
int num = rand()%45+1; // make and store a random number change 45 for more or less Balls.
return num; // return the random number.
}
// Harray() function create and fill an array with random numbers and some formatting.
void Harray()
{
int Balls[6]; // change the number in Balls[6] and in the for loop for more or less nrs. a row.
for(int x=0; x<=6; x++) //the loop to fill array with random numbers.
{
int a; // made to pass the Balls[x] data into so i can format output.
int m = Hrand(); // calling the Hrand() function and passing it's value in int m.
Balls[x] = m; // throwing it into the array tought i did this because of an error.
a = Balls[x]; // throwing it into int a because of an type error.
cout<<"["<<setfill('0')<<setw(02)<<a<<"]"; //format output with leading 0 if neccesary.
}
cout<<endl; // start new row on new line.
}
// Main function do the thing if compiler swallows the junk.
int main() // start the program.
{
int h; // int to store user cchoice.
srand(time(0)); // make rand more random.
cout<<"How many rows do you want to generate?"<<endl; // ask how many rows?
cin>>h; // store user input.
for(int i=h; h>0; h--) // produce rows from user input choice.
{
Harray(); // calling Harray function into action.
}
return 0; // return zero keep the comipler happy.
}
I would like to always have six diffrent numbers in a row but i don't see how to get there with the for loops i think the while loop is way to go but am open to any suggestion that will work. I'm just starting with c++ i might have overlooked some options.
int x=0;
while(x<6)
{
int a;format output.
int m = Hrand();value in int m.
Balls[x] = m; because of an error.
a = Balls[x];
cout<<"["<<setfill('0')<<setw(02)<<a<<"]";
x++;
}
Here, I also fixed a bug. Since Balls has 6 elements, the last element will be 5. Thus you want x<6 instead of x<=6. That goes for the for loop too.
One drawback of while loops is that you cannot declare local variables with them.
First of all, you should realize that the difference between a for loop and a while loop is mostly syntactic--anything you can do with one, you can also do with the other.
In this case, given what you've stated as your desired output, what you probably really want is something like this:
std::vector<int> numbers;
std::set<int> dupe_tracker;
while (dupe_tracker.size() < 6) {
int i = Hrand();
if (dupe_tracker.insert(i).second)
numbers.push_back(i);
}
The basic idea here is that dupe_tracker keeps a copy of each number you've generated. So, you generate a number, and insert it into the set. That will fail (and return false in retval.second) if the number is already in the set. So, we only add the number to the result vector if it was not already in the set (i.e., if it's unique).
How convert for-loop to while-loop
#include <iostream>
class T545_t
{
// private data attributes
int j;
public:
int exec()
{
// A for-loop has 3 parameters, authors often fill 2 of them with magic
// numbers. (magic numbers are usually discouraged, but are expected
// in for-loops)
// Here, I create names for these 3 for-loop parameters
const int StartNum = 2;
const int EndNum = 7;
const int StrideNum = 2;
std::cout << std::endl << " ";
for (int i = StartNum; i < EndNum; i += StrideNum ) {
std::cout << i << " " << std::flush;
}
std::cout << std::flush;
// A while-loop must use / provide each of these 3 items also, but
// because of the increased code-layout flexibility (compared to
// for-loop), the use of magic numbers should be discouraged.
std::cout << std::endl << " ";
j = StartNum;
do {
if (j >= EndNum) break;
std::cout << j << " " << std::flush;
j += StrideNum;
} while(true);
std::cout << std::flush;
std::cout << std::endl << " ";
j = StartNum;
while(true) {
if (j >= EndNum) break;
std::cout << j << " " << std::flush;
j += StrideNum;
}
std::cout << std::flush;
std::cout << std::endl << " ";
j = StartNum;
while(j < EndNum) {
std::cout << j << " " << std::flush;
j += StrideNum;
}
std::cout << std::endl;
return 0;
}
}; // class T545_t
int main(int , char** )
{
T545_t t545;
return(t545.exec());
}
Ask me where 'j' is declared?
This code is marked as C++, so in this case, I have declared 'j' in the private data attribute 'section' of this class definition. That is where you'd look for it, right?
If your c++ code does not have class, what's the point?

Coordinate system with an Ordinate and Abscissa

I'm currently having a problem making a code for a Coordinate system.
In the exercise I'm doing, I want to create a coordinate system with an Ordinate/Abscissa and a defined letter (for example dot A)
I must put information for 25 dots and it must control all dots with the same letter. They should be in a circle with a (0;0) coordinate beginning. If the information given about the 25 dots do not meet the set condition the selected dots must have new reentered information to meet the condition without changing the given values of the previous dots(which meet the expectations). It also should have all the information for dots which have 2 positive coordinates
here's the code I made. I'd be really thankful if someone helped me out.
#include <iostream>
#include <cmath>
#include <stdio.h>
using namespace std;
int main(){
int dotX[23];//tri masiva
int dotY[23];
char dotName[23];
for (int i = 0; i<23; i++){// Cikal za vavejdane na masivite
cout << "Abscisa \t" << i + 1 << endl;
cin >> dotX[i];
cout << "Ordinata \t" << i + 1 << endl;
cin >> dotY[i];
cout << "Ime na tochkata" << endl;
cin >> dotName[i];
if (i >= 1){//IF operatora i cikula za obhozhdane na masiva i presmqtane na distanciite
bool flag = true;
while (flag){
double distance = sqrt(pow(dotY[i] - dotY[i - 1], 2) + pow(dotX[i] - dotX[i - 1], 2));//Formula za presmqtane na razstoqniqta
if (distance <= 6) {
char broi;
broi = broi++;
cout << "abscisa \t" << i + 1 << endl;
cin >> dotX[i];
cout << "ordinata \t" << i + 1 << endl;
cin >> dotY[i];
}
else{
flag = false;
}
}
}
}
float i;
for (float i = 0; i > 10, i++;){
float(dotX < 10);
cout << dotName[i] << endl;
}
}
There are a few big problems with your code.
First of all, the syntax for (float i = 0; i > 10, i++;) is completely wrong. It compiles, but that's just a coincidence. The different command in the for loop control structure should be separated by semicolons (;), not commas (,). The correct code would then be for (float i = 0; i > 10; i++). By the way, you made a typo, I think you meant for (float i = 0; i < 10; i++) (otherwise the for loop never runs since i is initialized to 0 and 0 > 10 is false from the beginning).
Second of all, you're initializing the variable i twice: once with float i; and once in the for loop. That shouldn't compile, although with some compilers it does. There are two options on how to do. The first option is to declare the variable outside of the for loop and just assign it without initializing it in the for loop:
float i;
for(i = 0; i < 10; i++){
//some stuff
}
The second option is to simply declare it in the for loop as you did in the first loop:
for(float i = 0; i < 10; i++){
//some stuff
}
Another mistake that you made is to declare i as a float and then try to access dotName[i]. Whatever you put inside the brackets has to be of type int or something similar (unsigned int, long, etc). Putting a float variable inside those brackets won't compile just like that. If you want to index an array with a float, you need to tell the compiler that you want to convert it to an int like this: dotName[(int)i] or dotName[int(i)]. This is called a cast. However, in your case, I would recommend just declaring i as an int.
Also, float(dotX < 10); is completely wrong, I don't really understand what you're trying to do there. I think you meant to do float(dotX[i] < 10);, but that still doesn't make any sense. What you would be doing there would be converting a bool to a float and then doing nothing with the result. That compiles and isn't wrong, but is completely useless. As I said, I don't understand what you want to do there.
Also, broi = broi++; is correct but useless. broi++; is enough. The ++ operator increments broi by one by itself and then returns the result. What the ++ operator does internally is basically this:
int operator++(int &x){
x = x + 1;
return x;
}
So it already increments the variable automatically without you having to do anything. What you did is the same as doing this:
broi = broi + 1;
broi = broi;
Here, the first line represents the ++ operator and the second line represents the = operator. It's clear that the second line is useless, so you can just remove it. In the same way, in your code, you can remove broi =, leaving simply broi++;.
You also did a few things that aren't recommended, but work just fine since the C++ standard supports them.
First of all, using namespace std; is bad practice. It's recommended to omit it and add std:: in front of cin, cout and endl. If you want to know why using namespace std; is bad practice, it's well explained here. However, I must admit that I personally still use using namespace std; since I think it's simpler.
Second of all, the main function is supposed to return 0, so it's recommended to add return 0; at the end of the main function. The return value of the main function tells what made the program close. The value 0 means that the program closed when it was supposed to. Any other values mean that the program crashed. A complete list of what each return value means is available here. Note that C++ supports omitting return 0; and most compilers add it automatically if it is omitted, but it's still recommended to have it. Also, C doesn't support omitting return 0; and in C it will return whatever happens to be in the memory, making it looked like the program crashed when it ended normally.
Also, #include <stdio.h> is C and although it works in C++, it's not recommended. In C++, it's better to use #include <cstdio>. All standard libraries that end with .h in C can be used in C++ by removing .h and adding a c at the beginning. That's also the case with cmath: in C, it would be #include <math.h> and in C++, it's #include <cmath>.
A good version of your code would therefore be:
#include <iostream>
#include <cmath>
#include <cstdio>
int main(){
int dotX[23]; //tri masiva
int dotY[23];
char dotName[23];
for (int i = 0; i < 23; i++){ // Cikal za vavejdane na masivite
std::cout << "Abscisa \t" << i + 1 << std::endl;
std::cin >> dotX[i];
std::cout << "Ordinata \t" << i + 1 << std::endl;
std::cin >> dotY[i];
std::cout << "Ime na tochkata" << std::endl;
std::cin >> dotName[i];
if (i >= 1){ //IF operatora i cikula za obhozhdane na masiva i presmqtane na distanciite
bool flag = true;
while (flag){
double distance = sqrt(pow(dotY[i] - dotY[i - 1], 2) + pow(dotX[i] - dotX[i - 1], 2)); //Formula za presmqtane na razstoqniqta
if (distance <= 6) {
char broi;
broi++;
std::cout << "abscisa \t" << i + 1 << std::endl;
std::cin >> dotX[i];
std::cout << "ordinata \t" << i + 1 << std::endl;
std::cin >> dotY[i];
}
else{
flag = false;
}
}
}
}
for (int i = 0; i < 10; i++){
float(dotX[i] < 10); //Note that I don't understand what you're trying to do here, so I just changed it to something that compiles
std::cout << dotName[i] << std::endl;
}
}

C++ Long Division

Whilst working on a personal project of mine, I came across a need to divide two very large arbitrary numbers (each number having roughly 100 digits).
So i wrote out the very basic code for division (i.e., answer = a/b, where a and b are imputed by the user)and quickly discovered that it only has a precision of 16 digits! It may be obvious at this point that Im not a coder!
So i searched the internet and found a code that, as far as i can tell, uses the traditional method of long division by making a string(but too be honest im not sure as im quite confused by it). But upon running the code it gives out some incorrect answers and wont work at all if a>b.
Im not even sure if there's a better way to solve this problem than the method in the code below!? Maybe there's a simpler code??
So basically i need help to write a code, in C++, to divide two very large numbers.
Any help or suggestions are greatly appreciated!
#include <iostream>
#include <iomanip>
#include <cmath>
using namespace std; //avoids having to use std:: with cout/cin
int main (int argc, char **argv)
{
string dividend, divisor, difference, a, b, s, tempstring = ""; // a and b used to store dividend and divisor.
int quotient, inta, intb, diff, tempint = 0;
char d;
quotient = 0;
cout << "Enter the dividend? "; //larger number (on top)
cin >> a;
cout << "Enter the divisor? "; //smaller number (on bottom)
cin >> b;
//making the strings the same length by adding 0's to the beggining of string.
while (a.length() < b.length()) a = '0'+a; // a has less digits than b add 0's
while (b.length() < a.length()) b = '0'+b; // b has less digits than a add 0's
inta = a[0]-'0'; // getting first digit in both strings
intb = b[0]-'0';
//if a<b print remainder out (a) and return 0
if (inta < intb)
{
cout << "Quotient: 0 " << endl << "Remainder: " << a << endl;
}
else
{
a = '0'+a;
b = '0'+b;
diff = intb;
//s = b;
// while ( s >= b )
do
{
for (int i = a.length()-1; i>=0; i--) // do subtraction until end of string
{
inta = a[i]-'0'; // converting ascii to int, used for munipulation
intb = b[i]-'0';
if (inta < intb) // borrow if needed
{
a[i-1]--; //borrow from next digit
a[i] += 10;
}
diff = a[i] - b[i];
char d = diff+'0';
s = d + s; //this + is appending two strings, not performing addition.
}
quotient++;
a = s;
// strcpy (a, s);
}
while (s >= b); // fails after dividing 3 x's
cout << "s string: " << s << endl;
cout << "a string: " << a << endl;
cout << "Quotient: " << quotient << endl;
//cout << "Remainder: " << s << endl;
}
system ("pause");
return 0;
cin.get(); // allows the user to enter variable without instantly ending the program
cin.get(); // allows the user to enter variable without instantly ending the program
}
There are much better methods than that. This subtractive method is arbitrarily slow for large dividends and small divisors. The canonical method is given as Algorithm D in Knuth, D.E., The Art of Computer Programming, volume 2, but I'm sure you will find it online. I'd be astonished if it wasn't in Wikipedia somewhere.

Nan results when iterating using sin and cos functions

I'm compiling this program using Code::Blocks 10.05 however normally I will get about 10 iterations done before it starts producing Nan in every single output. I was wondering if this is a problem caused by using the cos and sin functions and if there was a decent work around to avoid this?
I have to produce a lot of iterates because I am working on a project for University so it has to be accurate too. I looked up a few articles about how to avoid using sin and cos though I need to follow a few formulas rigorously otherwise the results I produce may be inaccurate so I'm not sure whether to compromise.
struct Particle // Need to define what qualities our particle has
{
double dPosition;
double dAngle;
};
Particle Subject;
void M1(double &x, double &y) //Defines movement if particle doesn't touch inner boundary
{
x = x + 2*y;
}
double d = 0.25; //This can and will be changed when I need to find a distance between
// the two cricles at a later stage
void M2(double &x,double &y, double d) //Defines movement of a particle if it impacts the inner boundary
{
double z = asin(-(sin(y)+d*cos(x + y))/0.35);
double y1 = y;
y = asin(-0.35*sin(z) + d*cos(x + y + 2*z));
x = y + y1 + x + 2*z;
}
int main()
{
cout << "Please tell me where you want this particle to start positions-wise? (Between 0 and 2PI" << endl;
cin >> Subject.dPosition;
cout << "Please tell me the angle that you would like it to make with the normal? (Between 0 and PI/2)" << endl;
cin >> Subject.dAngle;
cout << "How far would you like the distances of the two middle circles to be?" << endl;
double d;
cin >> d;
// These two functions are to understand where the experiment begins from.
// I may add a function to change where the circle starts however I will use radius = 0.35 throughout
cout << "So position is: " << Subject.dPosition << endl;
cout << "And angle with the normal is: " << Subject.dAngle <<endl;
int n=0;
while (n <= 100) //This is used to iterate the process and create an array of Particle data points
{ // in order to use this data to build up Poincare diagrams.
{
while (Subject.dPosition > 2*M_PI)
Subject.dPosition = Subject.dPosition - 2*M_PI;
}
{
if (0.35 >= abs(0.35*cos(Subject.dPosition + Subject.dAngle)+sin(Subject.dAngle))) //This is the condition of hitting the inner boundary
M2(Subject.dPosition, Subject.dAngle, d); //Inner boundary collision
else
M1(Subject.dPosition, Subject.dAngle); // Outer boundary collision
};
cout << "So position is: " << Subject.dPosition << endl;
cout << "And angle with the normal is: " << Subject.dAngle <<endl;
n++;
}
return 0;
}
Nan is shown in c++ as an indication of infinite, zero devision, and some other variations of non representable numbers.
Edit:
As pointed by Matteo Itallia, inf is used for infinite/zero division. I found these approaches:
template<typename T>
inline bool isnan(T value) {
return value != value;
}
// requires #include <limits>
template<typename T>
inline bool isinf(T value) {
return std::numeric_limits<T>::has_infinity &&
value == std::numeric_limits<T>::infinity();
}
Reference: http://bytes.com/topic/c/answers/588254-how-check-double-inf-nan
If the value is outside of [-1,+1] and passed to asin(), the result will be nan
If you need to check for Nan, try the following
if( value != value ){
printf("value is nan\n");
}