Undefined errors with arrays in c++? - c++

Basically we're trying to make arrays accessible at irregular indexes with this new object IntArray, we have a couple header and .cpp files, take a look:
//intarray.h
#ifndef _IntArray_H
#define _IntArray_H
#include <iostream>
#include <string>
using namespace std;
class IntArray {
public:
IntArray(int n);
IntArray(int a, int b);
IntArray();
IntArray(const IntArray& copyarray);
int low();
int high();
void setName(string n);
int *array;
int size;
void operator+=(IntArray&);
int& operator[](int x);
IntArray& operator=(IntArray&);
int operator!=(IntArray&);
int operator==(IntArray&);
friend ostream& operator<<(ostream&, const IntArray&);
friend IntArray operator+(IntArray& a, IntArray& b);
private:
//PRIVATE DATA MEMBERS
int lo, hi;
string name;
};
#endif
Here is the next file, another header file
// iadrv.h
#ifndef _IADRV_H
#define _IADRV_H
#include "intarray.h"
int main();
void test1();
void test2();
void test3();
void test4();
void test5();
void test6();
void test7();
void test8();
void test9();
void test10();
void test11();
void test12();
void test13();
void test14();
void test15();
void test16();
void test17();
void test18();
void test19();
void test20();
void wait();
#endif
and lastly, here are the two .cpp files
//intarray.cpp
#include <iostream>
#include <fstream>
#include "IntArray.h"
#include <string>
extern ofstream csis;
using namespace std;
IntArray::IntArray() {
size = 10;
array = new int[size];
lo = 0;
hi = (size - 1);
}
IntArray::IntArray(int n) {
array = new int[n];
lo = 0;
hi = n - 1;
size = n;
}
IntArray::IntArray(int a, int b) {
if (b > a) {
size = (b - a) + 1;
array = new int[size];
lo = a;
hi = b;
}
if (b == a) {
size = 1;
array = new int[size];
lo = a;
hi = b;
}
else if (a > b) {
cout << "-ERROR: First argument cannot be larger than second argument. Program Halted-" << endl;
}
}
IntArray::IntArray(const IntArray& copyarray) {
IntArray::lo = copyarray.lo;
IntArray::hi = copyarray.hi;
IntArray::size = copyarray.size;
array = new int[size];
for (int i = lo; i <= hi; i++) {
array[i] = copyarray.array[i];
}
}
ostream& operator<<(ostream& ostr, const IntArray& target)
{
int offset = target.lo;
for (int i = target.lo; i <= target.hi; i++) {
ostr << target.name << "[" << i << "] = " << target.array[i] << endl;
}
return ostr;
}
void IntArray::operator+=(IntArray& target)
{
int* p1 = (target.array + target.lo);
if ((hi - lo) != (target.hi - target.lo)) {
cout << "-ERROR: For +=, both elements must have same # of elements. Program Halted-" << endl;
csis << "-ERROR: For +=, both elements must have same # of elements. Program Halted-" << endl;
}
else {
for (int i = lo; i <= hi; i++) {
array[i] = *(p1 + i) + *(array + i);
}
}
}
IntArray operator+(IntArray& tar1, IntArray& tar2)
{
IntArray sum(tar1.size);
int* p1, *p2;
p1 = (tar1.array + tar1.lo);
p2 = (tar2.array + tar2.lo);
if (!(tar1.size == tar2.size)) {
cout << "-ERROR: To use +, must have same # of elements. Program Halted-" << endl << endl;
csis << "-ERROR: To use +, must have same # of elements. Program Halted-" << endl << endl;
}
else {
for (int i = 0; i <= sum.size; i++) {
sum.array[i] = *(p1 + i) + *(p2 + i);
}
}
return IntArray(sum);
}
int& IntArray::operator[](int x)
{
/**
if (x < lo) {
cout << "-ERROR: Not in range. Program Halt-" << endl << endl;
csis << "-ERROR: Not in range. Program Halt-" << endl << endl;
}
if (x > hi) {
cout << "-ERROR: Not in range. Program Halt-" << endl << endl;
csis << "-ERROR: Not in range. Program Halt-" << endl << endl;
}
*/
return array[x];
}
int IntArray::operator!=(IntArray& target)
{
int difference = target.lo - IntArray::lo;
int check = 1;
if ((size) == (target.size)) {
for (int i = lo; i <= hi; i++) {
if (array[i] == target.array[i + difference]) {
check--;
}
}
}
else if (size != target.size) {
return check;
}
if (check < 0) {
check = 0;
}
return check;
}
int IntArray::operator==(IntArray& target)
{
int check = 0;
int difference = target.lo - IntArray::lo;
if (size == target.size) {
for (int i = lo; i <= hi; i++) {
if (array[i] == target.array[i + difference]) {
check++;
}
}
}
else if (!(size == target.size)) {
return 0;
}
if (check > 0) {
check = 1;
}
return check;
}
IntArray& IntArray::operator=(IntArray& target)
{
int difference = target.lo - IntArray::lo;
if (size != target.size) {
cout << "ERROR: Invalid assigment of two different sized arrays" << endl << endl << endl;
csis << "ERROR: Invalid assigment of two different sized arrays" << endl << endl << endl;
}
for (int i = IntArray::lo; i <= IntArray::hi; i++) {
array[i] = target.array[i + difference];
}
return *this;
}
void IntArray::setName(string n) {
IntArray::name = n;
}
int IntArray::low() {
return lo;
}
int IntArray::high() {
return hi;
}
This is the .cpp file with main
// iadrv.cpp - driver program for testing IntArray class
#include <iostream>
#include <iomanip>
#include <fstream>
#include <stdlib.h>
#include "iadrv.h"
using namespace std;
ofstream csis;
int main() {
csis.open("csis.txt");
test1();
test2();
test3();
/**
test4();
test5();
test6();
test7();
test8();
test9();
test10();
test11();
test12();
test13();
test14();
test15();
test16();
test17();
test18();
test19();
test20();
*/
csis.close();
}
void test1() {
cout << "1. Array declared with single integer: IntArray a(10);" << endl << endl;
csis << "1. Array declared with single integer: IntArray a(10);" << endl << endl;
IntArray a(10);
for (int i = a.low(); i <= a.high(); i++)
a[i] = i * 10;
a.setName("a");
cout << a << endl;
csis << a << endl;
wait();
}
void test2() {
cout << "2. Array declared with two integers: IntArray b(-3, 6);" << endl << endl;
csis << "2. Array declared with two integers: IntArray b(-3, 6);" << endl << endl;
IntArray b(-3, 6);
for (int i = b.low(); i <= b.high(); i++)
b[i] = i * 10;
b.setName("b");
cout << b << endl;
csis << b << endl;
wait();
}
void test3() {
cout << "3. Array declared with two integers: IntArray c(6, 8);" << endl << endl;
csis << "3. Array declared with two integers: IntArray c(6, 8);" << endl << endl;
IntArray c(6, 8);
cout << c.low() << endl;
cout << c.high() << endl;
for (int i = c.low(); i <= c.high(); i++) {
c[i] = i * 10;
cout << c[i] << " " << i << endl;
}
c.setName("c");
cout << c << endl;
csis << c << endl;
wait();
}
void test4() {
cout << "4. Array declared with two identical integers: IntArray d(5, 5);" << endl << endl;
csis << "4. Array declared with two identical integers: IntArray d(5, 5);" << endl << endl;
IntArray d(5, 5);
for (int i = d.low(); i <= d.high(); i++)
d[i] = i * 10;
d.setName("d");
cout << d << endl;
csis << d << endl;
wait();
}
void test5() {
cout << "5. Array declared with no integers: IntArray z;" << endl << endl;
csis << "5. Array declared with no integers: IntArray z;" << endl << endl;
IntArray z;
for (int i = z.low(); i <= z.high(); i++)
z[i] = i * 10;
z.setName("z");
cout << z << endl;
csis << z << endl;
wait();
}
void test6() {
cout << "6. Array declared with another object of type IntArray: IntArray c(6, 8);" << endl;
cout << " Intarray e(c);" << endl << endl;
csis << "6. Array declared with another object of type IntArray: IntArray c(6, 8);" << endl;
csis << " Intarray e(c);" << endl << endl;
IntArray c(6, 8);
for (int i = c.low(); i <= c.high(); i++)
c[i] = i * 10;
c.setName("c");
cout << c << endl;
csis << c << endl;
IntArray e(c);
e.setName("e");
cout << e << endl;
csis << e << endl;
wait();
}
void test7() {
cout << "7. Array assigned to another array w/ different indices: IntArray f(1, 4);" << endl;
cout << " IntArray g(5, 8);" << endl;
cout << " f = g;" << endl << endl;
csis << "7. Array assigned to another array w/ different indices: IntArray f(1, 4);" << endl;
csis << " IntArray g(5, 8);" << endl;
csis << " f = g;" << endl << endl;
IntArray f(1, 4);
for (int i = f.low(); i <= f.high(); i++)
f[i] = i * 10;
f.setName("f");
cout << f << endl;
csis << f << endl;
IntArray g(5, 8);
for (int i = g.low(); i <= g.high(); i++)
g[i] = i * 10;
g.setName("g");
cout << g << endl;
csis << g << endl;
wait();
f = g;
cout << f << endl;
cout << g << endl;
csis << f << endl;
csis << g << endl;
wait();
}
void test8() {
cout << "8. Multiple array assignment with different indices: IntArray j(3, 6);" << endl;
cout << " IntArray k(6, 9);" << endl;
cout << " IntArray l(1, 4);" << endl;
cout << " j = k = l;" << endl << endl;
csis << "8. Multiple array assignment with different indices: IntArray j(3, 6);" << endl;
csis << " IntArray k(6, 9);" << endl;
csis << " IntArray l(1, 4);" << endl;
csis << " j = k = l;" << endl << endl;
IntArray j(3, 6);
for (int i = j.low(); i <= j.high(); i++)
j[i] = i * 10;
j.setName("j");
cout << j << endl;
csis << j << endl;
IntArray k(6, 9);
for (int i = k.low(); i <= k.high(); i++)
k[i] = i * 10;
k.setName("k");
cout << k << endl;
csis << k << endl;
IntArray l(1, 4);
for (int i = l.low(); i <= l.high(); i++)
l[i] = i * 10;
l.setName("l");
cout << l << endl;
csis << l << endl;
wait();
j = k = l;
cout << j << endl;
cout << k << endl;
cout << l << endl;
csis << j << endl;
csis << k << endl;
csis << l << endl;
wait();
}
void test9() {
cout << "9. Overloaded equality operator (identical elements): IntArray m(3, 7);" << endl;
cout << " IntArray n(1, 5);" << endl;
cout << " m == n" << endl << endl;
csis << "9. Overloaded equality operator (identical elements): IntArray m(3, 7);" << endl;
csis << " IntArray n(1, 5);" << endl;
csis << " m == n" << endl << endl;
IntArray m(3, 7);
for (int i = m.low(); i <= m.high(); i++)
m[i] = i * 10;
m.setName("m");
cout << m << endl;
csis << m << endl;
IntArray n(1, 5);
for (int i = n.low(); i <= n.high(); i++)
n[i] = i * 10;
n.setName("n");
cout << n << endl;
csis << n << endl;
wait();
m = n;
cout << m << endl;
cout << n << endl;
cout << "Returns " << (m == n ? "True." : "False.") << endl << endl;
csis << m << endl;
csis << n << endl;
csis << "Returns " << (m == n ? "True." : "False.") << endl << endl;
wait();
}
void test10() {
cout << "10. Overloaded equality operator (different elements): IntArray o(3, 7);" << endl;
cout << " IntArray p(1, 5);" << endl;
cout << " o == p" << endl << endl;
csis << "10. Overloaded equality operator (different elements): IntArray o(3, 7);" << endl;
csis << " IntArray p(1, 5);" << endl;
csis << " o == p" << endl << endl;
IntArray o(3, 7);
for (int i = o.low(); i <= o.high(); i++)
o[i] = i * 10;
o.setName("o");
cout << o << endl;
csis << o << endl;
IntArray p(1, 5);
for (int i = p.low(); i <= p.high(); i++)
p[i] = i * 10;
p.setName("p");
cout << p << endl;
cout << "Returns " << (o == p ? "True." : "False.") << endl << endl;
csis << p << endl;
csis << "Returns " << (o == p ? "True." : "False.") << endl << endl;
wait();
}
void test11() {
cout << "11. Overloaded equality operator (different size arrays): IntArray q(1, 3);" << endl;
cout << " IntArray r(1, 4);" << endl;
cout << " q == r;" << endl << endl;
csis << "11. Overloaded equality operator (different size arrays): IntArray q(1, 3);" << endl;
csis << " IntArray r(1, 4);" << endl;
csis << " q == r;" << endl << endl;
IntArray q(1, 3);
for (int i = q.low(); i <= q.high(); i++)
q[i] = i * 10;
q.setName("q");
cout << q << endl;
csis << q << endl;
IntArray r(1, 4);
for (int i = r.low(); i <= r.high(); i++)
r[i] = i * 10;
r.setName("r");
cout << r << endl;
cout << "Returns " << (q == r ? "True." : "False.") << endl << endl;
csis << r << endl;
csis << "Returns " << (q == r ? "True." : "False.") << endl << endl;
wait();
}
void test12() {
cout << "12. Overloaded inequality operator (identical elements): IntArray s(3, 7);" << endl;
cout << " IntArray t(1, 5);" << endl;
cout << " s != t;" << endl << endl;
csis << "12. Overloaded inequality operator (identical elements): IntArray s(3, 7);" << endl;
csis << " IntArray t(1, 5);" << endl;
csis << " s != t;" << endl << endl;
IntArray s(3, 7);
for (int i = s.low(); i <= s.high(); i++)
s[i] = i * 10;
s.setName("s");
cout << s << endl;
csis << s << endl;
IntArray t(1, 5);
for (int i = t.low(); i <= t.high(); i++)
t[i] = i * 10;
t.setName("t");
cout << t << endl;
csis << t << endl;
wait();
s = t;
cout << s << endl;
cout << t << endl;
cout << "Returns " << (s != t ? "True." : "False.") << endl << endl;
csis << s << endl;
csis << t << endl;
csis << "Returns " << (s != t ? "True." : "False.") << endl << endl;
wait();
}
void test13() {
cout << "13. Overloaded inequality operator (different elements): IntArray u(3, 7);" << endl;
cout << " IntArray v(1, 5);" << endl;
cout << " u != v;" << endl << endl;
csis << "13. Overloaded inequality operator (different elements): IntArray u(3, 7);" << endl;
csis << " IntArray v(1, 5);" << endl;
csis << " u != v;" << endl << endl;
IntArray u(3, 7);
for (int i = u.low(); i <= u.high(); i++)
u[i] = i * 10;
u.setName("u");
cout << u << endl;
csis << u << endl;
IntArray v(1, 5);
for (int i = v.low(); i <= v.high(); i++)
v[i] = i * 10;
v.setName("v");
cout << v << endl;
cout << "Returns " << (u != v ? "True." : "False.") << endl << endl;
csis << v << endl;
csis << "Returns " << (u != v ? "True." : "False.") << endl << endl;
wait();
}
void test14() {
cout << "14. Overloaded inequality operator (different size arrays): IntArray w(1, 3);" << endl;
cout << " IntArray x(1, 4);" << endl;
cout << " w != x;" << endl << endl;
csis << "14. Overloaded inequality operator (different size arrays): IntArray w(1, 3);" << endl;
csis << " IntArray x(1, 4);" << endl;
csis << " w != x;" << endl << endl;
IntArray w(1, 3);
for (int i = w.low(); i <= w.high(); i++)
w[i] = i * 10;
w.setName("w");
cout << w << endl;
csis << w << endl;
IntArray x(1, 4);
for (int i = x.low(); i <= x.high(); i++)
x[i] = i * 10;
x.setName("x");
cout << x << endl;
cout << "Returns " << (w != x ? "True." : "False.") << endl << endl;
csis << x << endl;
csis << "Returns " << (w != x ? "True." : "False.") << endl << endl;
wait();
}
void test15() {
cout << "15. Sum of two arrays assigned to third array: IntArray a(1, 5);" << endl;
cout << " IntArray b(4, 8);" << endl;
cout << " IntArray c = a + b;" << endl << endl;
csis << "15. Sum of two arrays assigned to third array: IntArray a(1, 5);" << endl;
csis << " IntArray b(4, 8);" << endl;
csis << " IntArray c = a + b;" << endl << endl;
IntArray a(1, 5);
for (int i = a.low(); i <= a.high(); i++)
a[i] = i * 10;
a.setName("a");
cout << a << endl;
csis << a << endl;
IntArray b(4, 8);
for (int i = b.low(); i <= b.high(); i++)
b[i] = i * 10;
b.setName("b");
cout << b << endl;
csis << b << endl;
wait();
IntArray c = a + b;
c.setName("c");
cout << c << endl;
csis << c << endl;
wait();
}
void test16() {
cout << "16. Sum of two arrays assigned to first array: IntArray d(10, 13);" << endl;
cout << " IntArray e(30, 33);" << endl;
cout << " d += e;" << endl << endl;
csis << "16. Sum of two arrays assigned to first array: IntArray d(10, 13);" << endl;
csis << " IntArray e(30, 33);" << endl;
csis << " d += e;" << endl << endl;
IntArray d(10, 13);
for (int i = d.low(); i <= d.high(); i++)
d[i] = i * 10;
d.setName("d");
cout << d << endl;
csis << d << endl;
IntArray e(30, 33);
for (int i = e.low(); i <= e.high(); i++)
e[i] = i * 10;
e.setName("e");
cout << e << endl;
csis << e << endl;
d += e;
cout << d << endl;
csis << d << endl;
wait();
}
void test17() {
cout << "17. Array declared with illegal array bounds: IntArray f(5, 2);" << endl << endl;
csis << "17. Array declared with illegal array bounds: IntArray f(5, 2);" << endl << endl;
IntArray f(5, 2);
for (int i = f.low(); i <= f.high(); i++)
f[i] = i * 10;
f.setName("f");
cout << f << endl;
csis << f << endl;
wait();
}
void test18() {
cout << "18. Array with index out of range: IntArray g(10);" << endl;
cout << " g[10] = 1;" << endl << endl;
csis << "18. Array with index out of range: IntArray g(10);" << endl;
csis << " g[10] = 1;" << endl << endl;
IntArray g(10);
for (int i = g.low(); i <= g.high(); i++)
g[i] = i * 10;
g.setName("g");
cout << g << endl;
csis << g << endl;
g[10] = 1;
wait();
}
void test19() {
cout << "19. Arrays with length mismatch: IntArray m(1, 4);" << endl;
cout << " IntArray n(2, 4);" << endl;
cout << " m = n;" << endl << endl;
csis << "19. Arrays with length mismatch: IntArray m(1, 4);" << endl;
csis << " IntArray n(2, 4);" << endl;
csis << " m = n;" << endl << endl;
IntArray m(1, 4);
for (int i = m.low(); i <= m.high(); i++)
m[i] = i * 10;
m.setName("m");
cout << m << endl;
csis << m << endl;
IntArray n(2, 4);
for (int i = n.low(); i <= n.high(); i++)
n[i] = i * 10;
n.setName("n");
cout << n << endl;
csis << n << endl;
wait();
m = n;
cout << m << endl;
cout << n << endl;
csis << m << endl;
csis << n << endl;
wait();
}
void test20() {
cout << "20. Array subscript operator: IntArray o(7, 8);" << endl;
cout << " o[7] = 25;" << endl;
cout << " o[8] = o[7];" << endl << endl;
csis << "20. Array subscript operator: IntArray o(7, 8);" << endl;
csis << " o[7] = 25;" << endl;
csis << " o[8] = o[7];" << endl << endl;
IntArray o(7, 8);
for (int i = o.low(); i <= o.high(); i++)
o[i] = i * 10;
o.setName("o");
cout << o << endl;
csis << o << endl;
o[7] = 25;
o[8] = o[7];
cout << o << endl;
csis << o << endl;
wait();
}
void wait() {
char buf;
cout << "Press any key to continue." << endl;
cin.get(buf);
}
The issue is when I try to run and compile in test3(), it'll output correctly SOMETIMES, but other times i'll rebuild the solution and it'll give garbage values despite having same code. It's very odd, and I can't seem to understand why it's doing this

Consider test2, and what happens when you access b[-3]
especially your implementation of int& IntArray::operator[](int x) where you do
int& IntArray::operator[](int x)
{
return array[x];
}
you are returning a reference to bogus memory. (An int that is 3 locations before the beginning of your allocated array)
Modify your code like this:
return array[x-lo];
Oh, and by the way, use std::vector.

Related

Football tournament with matrix

I'm trying to make a football tournament in C++, in which the user inputs the name of the teams(8 teams) and then each team has to play with the other one 1 time. Firstly, I don't know how to read the team names, I mean I tried to use .getline or just cin of a char array, but then I need to put the teams into the matrix and after the final game my program should print the table. So there's the first question: how to read the names and basically make the program think they are numbers or does it work with just with names, no need to use int? And then the users inputs the result for every game, but here comes the hard part. After all the results have been introduced, the matrix rotates cyclic and then the result stored in the variables(you will see in code victory/losses) overwrites themselves, so at the end, I cannot print the right table. So that's the second question: How can I make them store to the right 'team' while they rotate? Sorry if I didn't quite explain very well how it works, hope you understand it. Cheers!
// FOOTBALL TOURNAMENT
int map[2][4];
for (int i = 0; i < 2; i++) {
for (int j = 0; j < 4; j++) {
cout << "map[" << i << "][" << j << "]= ";
cin >> map[i][j];
}
}
cout << "The map looks like this:" << endl;
for (int i = 0; i < 2; i++) {
for (int j = 0; j < 4; j++) {
cout << map[i][j] << " ";
}
cout << endl;
}
map[0][0] = 1;
int temp = 0, temp2 = 0, temp3 = 0, temp4 = 0, temp5 = 0, temp6 = 0;
int a, b, c, d, e, f, g, h, round = 0;
int victory_m00(0), losses_m10(0), victory_m10(0), losses_m00(0), victory_m01(0), losses_m11(0), victory_m11(0), losses_m01(0);
int victory_m02(0), losses_m12(0), victory_m12(0), losses_m02(0), victory_m03(0), losses_m13(0), victory_m13(0), losses_m03(0);
do
{
// Insert result for every game
cout << "Enter the result of the first game between " << map[0][0] << " vs. " << map[1][0] << endl;
cin >> a >> b;
if (a > b) {
victory_m00++;
losses_m10++;
}
else if (a < b)
{
victory_m10++;
losses_m00++;
}
cout << "Enter the result of the first game between: " << map[0][1] << " vs. " << map[1][1] << endl;
cin >> c >> d;
if (c > d) {
victory_m01++;
losses_m11++;
}
else if (c < d)
{
victory_m11++;
losses_m01++;
}
cout << "Enter the result of the first game between: " << map[0][2] << " vs. " << map[1][2] << endl;
cin >> e >> f;
if (e > f) {
victory_m02++;
losses_m12++;
}
else if (e < f)
{
victory_m12++;
losses_m02++;
}
cout << "Enter the result of the first game between: " << map[0][3] << " vs. " << map[1][3] << endl;
cin >> g >> h;
if (g > h) {
victory_m03++;
losses_m13++;
}
else if (g < h)
{
victory_m13++;
losses_m03++;
}
round++;
// Map switching
temp = map[1][0];
map[1][0] = map[0][1];
temp2 = map[1][1];
map[1][1] = temp;
temp3 = map[1][2];
map[1][2] = temp2;
temp4 = map[1][3];
map[1][3] = temp3;
temp5 = map[0][3];
map[0][3] = temp4;
temp6 = map[0][2];
map[0][2] = temp5;
map[0][1] = temp6;
// Table calculating and printing ~ also this has to be outside the loop (but at first i wanted to print the table after every 'round'
cout << "This is how the table looks like after the " << round << " round: \n";
cout << map[0][0] << " has: " << victory_m00 << " victory(-ies) and " << losses_m00 << " loss-es!\n";
cout << map[0][1] << " has: " << victory_m01 << " victory(-ies) and " << losses_m01 << " loss-es!\n";
cout << map[0][2] << " has: " << victory_m02 << " victory(-ies) and " << losses_m02 << " loss-es!\n";
cout << map[0][3] << " has: " << victory_m03 << " victory(-ies) and " << losses_m03 << " loss-es!\n";
cout << map[1][0] << " has: " << victory_m10 << " victory(-ies) and " << losses_m10 << " loss-es!\n";
cout << map[1][1] << " has: " << victory_m11 << " victory(-ies) and " << losses_m11 << " loss-es!\n";
cout << map[1][2] << " has: " << victory_m12 << " victory(-ies) and " << losses_m12 << " loss-es!\n";
cout << map[1][3] << " has: " << victory_m13 << " victory(-ies) and " << losses_m13 << " loss-es!\n";
cout << endl;
cout << endl;
} while (map[0][1] != 2);
```

Multiplying elements in array not working in c++?

I am trying to make a simple program in c++ that takes the price and number of items purchases, stores it in arrays, and then outputs the totals for each item in a tabular format. However, when I multiply the numbers in my code, I get totally strange answers! Can someone please enlighten me as to what's going on?
Code:
#include <iostream>
using namespace std;
int main(int argc, _TCHAR* argv[]) {
float price[4], tot[4];
int amt[4];
cout << "Please enter the price and amount of 4 items:\n";
for (int i = 0; i<4; i++) {
cout << "Price of item " << i + 1 << ": ";
cin >> price[i];
cout << "Amount of item " << i + 1 << ": ";
cin >> amt[i];
if (price[i] <= 0 || amt[i] <= 0) {
cout << "Invalid Input Entry!\n";
break;
}
tot[i] = price[i] * amt[i]; // I can't really see how I could have messed this up...
}
cout << "Total\t\tPrice\t\tAmount\n";
cout << "-----\t\t-----\t\t------\n";
for (int i = 0; i < 4; i++) {
cout << "$" << fixed << cout.precision(2) << tot[i] << "\t\t$" << price[i] << "\t\t" << amt[i] << endl;
}
system("pause");
return 0;
}
Output:
The problem is that you are outputting the return value of cout.precision(2) (which returns the previous precision, in this case 6 initially and then 2 afterwards) in front of each total price.
You need to either:
not pass the return value of cout.precision() to operator<<:
cout << "$" << fixed;
cout.precision(2);
cout << tot[i] << ...
or, call precision() one time before entering the loop:
cout.precision(2);
for (int i = 0; i < 4; i++) {
cout << "$" << fixed << tot[i] << "\t\t$" << price[i] << "\t\t" << amt[i] << endl;
}
use the std::setprecision() stream manipulator instead of calling cout.precision() directly:
#include <iomanip>
for (int i = 0; i < 4; i++) {
cout << "$" << fixed << setprecision(2) << tot[i] << "\t\t$" << price[i] << "\t\t" << amt[i] << endl;
}
or
#include <iomanip>
cout << setprecision(2);
for (int i = 0; i < 4; i++) {
cout << "$" << fixed << tot[i] << "\t\t$" << price[i] << "\t\t" << amt[i] << endl;
}
On a side note, you should not use \t characters to control the formatting of your table. Use stream manipulators like std::setw(), std::left, etc instead:
#include <iostream>
#include <sstream>
#include <iomanip>
#include <cstdlib>
using namespace std;
const int maxItems = 4;
string moneyStr(float amount)
{
ostringstream oss;
// in C++11 and later, you can replace this with std::put_money() instead:
// http://en.cppreference.com/w/cpp/io/manip/put_money
//
// oss << showbase << put_money(amount);
oss << "$" << fixed << setprecision(2) << amount;
return oss.str();
}
int main(int argc, _TCHAR* argv[])
{
float price[maxItems], tot[maxItems];
int amt[maxItems];
int cnt = 0;
cout << "Please enter the price and amount of " << maxItems << " items:" << endl;
for (int i = 0; i < maxItems; ++i)
{
cout << "Price of item " << i + 1 << ": ";
cin >> price[i];
cout << "Amount of item " << i + 1 << ": ";
cin >> amt[i];
if (price[i] <= 0 || amt[i] <= 0) {
cout << "Invalid Input Entry!" << endl;
break;
}
tot[i] = price[i] * amt[i];
++cnt;
}
cout << left << setfill(' ');
cout << setw(16) << "Total" << setw(16) << "Price" << setw(16) << "Amount" << endl;
cout << setw(16) << "-----" << setw(16) << "-----" << setw(16) << "------" << endl;
for (int i = 0; i < cnt; i++) {
cout << setw(16) << moneyStr(tot[i]) << setw(16) << moneyStr(price[i]) << setw(16) << amt[i] << endl;
}
system("pause");
return 0;
}
Live Demo

Cannot print buffer address

I want to test the following code, however I get a compilation error. The thing that confuse me is that the way and create and print pd1 and pd2 are the same as pd3 and pd4, but the compiler complains about pd3 and pd4 when I print.
const int BUF = 512;
const int N = 5;
char buffer[BUF]; // chunk of memory
int main(){
using namespace std;
double *pd1, *pd2;
int i;
cout << "Calling new and placement new:\n";
pd1 = new double[N]; // use heap
pd2 = new (buffer) double[N]; // use buffer array
for (i = 0; i < N; i++)
pd2[i] = pd1[i] = 1000 + 20.0*i;
cout << "Buffer addresses:\n" << " heap: " << pd1 << " static: " << (void *)buffer << endl;
cout << "Buffer contents:\n";
for(i = 0; i < N; i++) {
cout << pd1[i] << " at " << &pd1[i] << "; ";
cout << pd2[i] << " at " << &pd2[i] << endl;
}
cout << "\nCalling new and placement new a second time:\n";
double *pd3, *pd4;
pd3 = new double[N];
pd4 = new (buffer) double[N];
for(i = 0; i < N; i++)
pd4[i] = pd3[i] = 1000 + 20.0 * i;
cout << "Buffer contents:\n";
for (i = 0; i < N; i++) {
cout << pd3[i] < " at " << &pd3[i] << "; ";
cout << pd4[i] < " at " << &pd4[i] << endl;
}
return 0;
}
Compilation error:
newplace.cpp: In function ‘int main()’:
newplace.cpp:33:36: error: invalid operands of types ‘const char [5]’ and ‘double*’ to binary ‘operator<<’
cout << pd3[i] < " at " << &pd3[i] << "; ";
^
newplace.cpp:34:36: error: invalid operands of types ‘const char [5]’ and ‘double*’ to binary ‘operator<<’
cout << pd4[i] < " at " << &pd4[i] << endl;
You missing one < symbol here
cout << pd3[i] < " at " << &pd3[i] << "; ";
cout << pd4[i] < " at " << &pd4[i] << endl;
Try
cout << pd3[i] << " at " << &pd3[i] << "; ";
cout << pd4[i] << " at " << &pd4[i] << endl;
You only put one < in the stream where you are trying to print out the buffer contents.
cout << pd3[i] < " at " << &pd3[i] << "; "; // there is only one <
cout << pd4[i] < " at " << &pd4[i] << endl; // ^
Make sure you have two <'s in the stream insertion operator.
cout << pd3[i] << " at " << &pd3[i] << "; ";
cout << pd4[i] << " at " << &pd4[i] << endl;

Lining columns up

Solved!
This is what I wrote:
cout << setw(4) << "Students";
cout << setw(20) << "Hours Worked";
cout << setw(20) << "of Total Hours";
cout << endl;
for (int i = 0; i < students; i++)
{
cout << setw(20);
cout << names[i];
cout << setw(10) << hours[i];
cout << setw(10) << percent[i];
cout << endl;
}
But if the first name is a few characters sorter or bigger than second name, they become misaligned. How would I keep each column aligned equally?
Try something like this:
#include<iostream>
#include <iomanip>
#include<string>
using namespace std;
int main()
{
int students = 5;
string names[5] = {"a","bccc","c","d","ecsdfsdfasdasasf"};
int hours[5] = {1,2,3,4,5};
int percent[5] = {10,20,30,40,54};
string column("Students");
int maxStringSize = 0;
int sizeOfStudentColumn = column.length();
for(int i = 0; i < 5; ++i)
{
if(maxStringSize < names[i].length())
maxStringSize = names[i].length();
}
if(sizeOfStudentColumn > maxStringSize)
maxStringSize = sizeOfStudentColumn;
cout<<"max size: "<<maxStringSize<<endl;
cout << setw(4) << "Students";
cout << setw(maxStringSize + 5) << "Hours Worked";
cout << setw(20) << "of Total Hours";
cout << endl;
for (int i = 0; i < students; i++)
{
// cout << setw(20);
cout << names[i];
int diff = maxStringSize - names[i].length();
cout << setw(diff + 5 ) << hours[i];
cout << setw(20) << percent[i];
cout << endl;
}
}

How to sort alphabetically in c++ programming

I'm trying to sort alphabetically by team for my program, but not having any luck. If there is any hints or advice out there I would appreciate it. Below is the program I have minus the data input. Basically I just want to know how I would go about specifically sorting only by team in alphabetical order.
nflrecievers data[100];
ifstream fin;
fin.open("data.txt");
ofstream fout;
fout.open("validationReport.txt");
int i = 0;
while(!fin.eof())
{
fin >> data[i].fname >> data[i].lname >> data[i].team >> data[i].rec >> data[i].yards >> data[i].avgyrds_percatch >> data[i].tds >> data[i].longest_rec >> data[i].recpasttwenty_yrds >> data[i].yrds_pergame >> data[i].fumbles >> data[i].yac >> data[i].first_dwns ;
i = i + 1;
}
int a;
int b;
cout << " Select NFL Receivers Statistics. Input 1-4 " << endl;
cout << " 1) Receivers with 25+ Rec and 300+ Yards. " << endl;
cout << " 2) Recievers with 3+ TDs and 3+ Rec over 20 Yards. " << endl;
cout << " 3) Recievers with 100+ Yards per game and 15+ First Downs. " << endl;
cout << " 4) Veiw Total Recievers Statistics. " << endl;
cin >> a;
int c = 0;
if (a==1)
{
cout << " Receivers with 25+ Rec and 300+ Yards. " << endl;
while( c < i-1)
{
if(data[c].rec > 25 && data[c].yards > 300)
{
cout << endl;
cout << data[c].fname << " " << data[c].lname << " " << data[c].team << endl;
cout << " Rec: " << data[c].rec << " Yards: " << data[c].yards << endl;
cout << endl;
}
c++;
}
}
else if(a==2)
{
cout << " Recievers with 3+ TDs and 3+ Receptions past 20 Yards. " << endl;
while( c < i-1)
{
if(data[c].tds > 3 && data[c].recpasttwenty_yrds > 3)
{
cout << endl;
cout << data[c].fname << " " << data[c].lname << " " << data[c].team << endl;
cout << " TDs: " << data[c].tds << " Receptions past 20 Yards: " << data[c].recpasttwenty_yrds << endl;
cout << endl;
}
c++;
}
}
else if(a==3)
{
cout << " Recievers who average over 100+ yards per game and 15+ First Downs. " << endl;
while( c < i-1)
{
if(data[c].yrds_pergame > 100 && data[c].first_dwns > 15)
{
cout << endl;
cout << data[c].fname << " " << data[c].lname << " " << data[c].team << endl;
cout << " Average Yards per game: " << data[c].yrds_pergame << " First Downs: " << data[c].first_dwns << endl;
cout << endl;
}
c++;
}
}
else if(a==4)
{
cout << " Select a Reciever: " << endl;
while( c < i-1)
{
cout << c << ") " << data[c].fname << " " << data[c].lname << endl;
c++;
}
cout << " Total NFL Receivers Statistics. " << endl;
cin >> b;
cout << data[b].fname << " " << data[b].lname << endl;
cout << " Team: " << data[b].team << endl;
cout << " Receptions: " << data[b].rec << endl;
cout << " Yards: " << data[b].yards << endl;
cout << " Average Yards Per Catch: " << data[b].avgyrds_percatch << endl;
cout << " Longest Reception: " << data[b].longest_rec << endl;
cout << " Receptions over 20 Yards: " << data[b].recpasttwenty_yrds << endl;
cout << " Yards per game " << data[b].yrds_pergame << endl;
cout << " Fumbles: " << data[b].fumbles << endl;
cout << " Average Yards After Catch " << data[b].yac << endl;
cout << " Total First Downs: " << data[b].first_dwns << endl;
}
return 0;
}
std::sort(std::begin(data), std::end(data),
[](const nflrecievers& a, const nflrecievers& b) { return a.team < b.team; });
I would use std::sort
bool compare_teams(const nflrecievers &a, const nflrecievers &b) {
return a.team < b.team;
}
int i = 0;
while(!fin.eof())
{
fin >> data[i].fname >> data[i].lname >> data[i].team >> data[i].rec >> data[i].yards >> data[i].avgyrds_percatch >> data[i].tds >> data[i].longest_rec >> data[i].recpasttwenty_yrds >> data[i].yrds_pergame >> data[i].fumbles >> data[i].yac >> data[i].first_dwns ;
i = i + 1;
}
std::sort(data, data+i, compare_teams);
for (int i=0;i<c-1;i++)
for (int j=0;j<c-1;j++)
if (data[j].team>data[j+1].team)
{
nflrecievers temp = data[j];
data[j] = data[j+1];
data[j+1] = temp;
}
another solution:
int compare(const void *v1, const void *v2)
{
nflrecievers p1 = *(nflrecievers *)v1, p2 = *(nflrecievers *)v2;
return strcmp(p1.team,p2.team);
}
qsort(data,c,sizeof(data),compare);