I created a random, and its size is created randomly. Then I assign random values to this array. Finally, I want to write odd values and even values into different arrays. But the last two for loops display wrong values for evenArray and oddArray.
Where is the error? Please help me identify the error.
#include <iostream>
#include <time.h>
#include <stdlib.h>
using namespace std;
int main()
{
srand(time(0));
int arraySize = rand() % 10 + 4;
cout << "Array Size : " << arraySize << endl;
int myArray[arraySize];
int oddIndex = 0;
int evenIndex = 0;
int oddArray[oddIndex];
int evenArray[evenIndex];
for( int m = 0 ; m < arraySize ; m++)
{
myArray[m] = rand() % 100 + 90 ;
cout << m << "th value is : " << myArray[m] << endl;
}
for( int i = 0; i < arraySize ; i++)
{
if( myArray[i] % 2 == 0)
{
evenArray[evenIndex] = myArray[i];
cout << "EVEN ARRAY " << evenIndex << "th element is " << evenArray[evenIndex] << endl;
evenIndex++;
}
else
{
oddArray[oddIndex] = myArray[i];
cout << "ODD ARRAY " << oddIndex << "th element is " << oddArray[oddIndex] << endl;
oddIndex++;
}
}
cout << "The total number of even array elements : " << evenIndex << endl;
cout << "The total number of odd array elements : " << oddIndex << endl;
cout << "/////////////////////////////////////////\n";
cout << "EVEN VALUES" << endl;
for( int i = 0 ; i < evenIndex ; i++ )
{
cout << i << "th even value is: " << evenArray[i] << endl;
}
cout << "/////////////////////////////////////////\n";
cout << "ODD VALUES" << endl;
for( int p = 0 ; p < oddIndex ; p++ )
{
cout << p << "th odd value is : " << oddArray[p] << endl;
}
}
int oddIndex = 0;
int evenIndex = 0;
int oddArray[oddIndex];
int evenArray[evenIndex];
As you can see you are initializing oddArray and evenArray with 0 size.What you can do is declare both arrays of size arraySize,or better you can use vectors
You use wrong initialization of arrays length
int oddArray[oddIndex];
int evenArray[evenIndex];
In this lines you create two arrays of zero length. Further use to these arrays will lead to undefined behaviors.
If you need an array with dynamically changing length you should use std::vector.
Related
I wrote the below code (for homework) that is counting letters and numbers and generates a frequency table.
My question is: how to stop the frequency generation when the letter or number does not exist?
With the code I wrote, the program is counting every letter that are being fed to it but is also publishing a line for every possible letter/number in the ASCII code.
I hope I asked my question right and I appreciate any help or advice!
#include <iostream>
#include <string>
using namespace std;
int countingLetters(string someWords);
int countingNumbers(string someWords);
int frequency(string someWords, double totalChar);
int main() {
string someWords;
cout << "Write a some words: " << endl;
getline(cin, someWords);
cout << "You wrote:" << someWords << '\n';
cout << "Your sentence has " << someWords.length() << " characters." << '\n';
double totalChar = someWords.length();
cout << "Your sentence has " << countingLetters(someWords) << " letters." << '\n';
cout << "Your sentence has " << countingNumbers(someWords) << " numbers." << '\n';
cout << "Frequency of signs and letters :" << endl;
frequency(someWords, totalChar);
return 0;
}
int countingLetters(string someWords) {
int count = 0;
for (int i = 0; i < someWords.length(); i++) {
if (someWords[i] >= 'a' && someWords[i] <= 'z')
count++;
}
return count;
}
int countingNumbers(string someWords) {
int count = 0;
for (int i = 0; i < someWords.length(); i++) {
if (isdigit(someWords[i]) != 0)
count++;
}
return count;
}
int frequency(string someWords, double totalChar) {
cout << " Letter" << '\t' << "Antal" << '\t' << "Procent" << endl;
int frequency[255]={0};
for (int i = 0; i < someWords.length(); i++) {
char c = someWords[i];
if (isdigit(c) != 0)
frequency[c]++;
if (isalpha(c) != 0)
frequency[c]++;
}
for (int i = 0; i < sizeof(frequency); i++) {
if(frequency[i]>0)
cout << '\t' << static_cast<char>(i) << '\t' << frequency[i] << '\t' << frequency[i]/totalChar << endl;
}
return 0;
}
sizeof(frequency) is the size of the frequency array in bytes. You want the number of elements which is the size in bytes if the array divided by the size in bytes of one array element:
This is the number of elements of the frequency array:
sizeof(frequency) / sizeof(frequency[0])
But as you are using C++ you shouln't use raw arrays but std::array:
#include <array>
...
int frequency(string someWords, int totalChar) {
cout << " Letter" << '\t' << "Antal" << '\t' << "Procent" << endl;
std::array<int, 255> frequency{0};
for (int i = 0; i < someWords.length(); i++) {
char c = someWords[i];
if (isdigit(c) != 0)
frequency[c]++;
if (isalpha(c) != 0)
frequency[c]++;
}
int x = frequency.max_size();
for (int i = 0; i < frequency.max_size(); i++) {
if (frequency[i]>0)
cout << '\t' << static_cast<char>(i) << '\t' << frequency[i] << '\t' << frequency[i] / totalChar << endl;
}
return 0;
}
There is still room for improvement.
I am failing to reach expected output when testing my 'grow'and 'subArray' functions. I've tried dereferencing back and forth in the function and also in main(). I'm wondering if there's something wrong with my memory allocation that is causing the lapse. I am extremely stuck and was hoping someone could potentially see something that I am missing, thanks.
#include <iostream>
#include <iomanip>
using namespace std;
bool isSorted(int *arr, int size){
for(int index = 0; index < size - 1; index ++){
if(*(arr + index) > *(arr + index + 1)){
return false;
}
}
return true;
}
double chain (int totalInches, int *feet, int *inches){
*feet = totalInches/12;
*inches = totalInches%12;
return *(feet)*3.49 + *(inches)*.30;
}
int *grow (int *arr, int size){
int *newArray;
newArray = new int[size*2]; //alocate new array
for(int i = 0; i < size*2; i+=2){
*(newArray + i) = *(arr+i);
*(newArray + i + 1) = *(arr+i);
}
return newArray;
}
int *duplicateArray (int *array, int size) {
int *newArray;
if (size <= 0)
return NULL;
newArray = new int [size]; //allocate new array
for (int index = 0; index < size; index++){
newArray[index] = array[index]; //copy to new array
}
return newArray;
}
int *subArray( int *array, int start, int length){
int *result = duplicateArray(array,5);
return result;
}
void showArray( int *arr, int size){
for(int i = 0; i < size; i ++)
{
cout << *(arr + i) << " ";
}
}
int main(){
int size = 8;
int testArray[] = {1,2,3,4,5,6,7,8};
cout << "testing isSorted: " << endl;
cout << "test data array 1: ";
showArray(testArray, size);
cout << endl;
cout << "Expected result: true" << endl;
cout << "Actual result: " << boolalpha << isSorted(testArray, size);
cout << endl;
int testArray2[]= {8,7,6,5,4,3,2,1};
cout << "test data array 2: ";
showArray(testArray2, size);
cout << endl;
cout << "Expected result: false" << endl;
cout << "Actual result: " << boolalpha << isSorted(testArray2, size);
cout << endl << endl << endl;
int chainTest = 53;
cout << "Checking chain for 53 inches: " << endl;
cout << "Expected result: 15.46 " << " " << "feet: 4 " <<
" " << "inches: 5"<< endl;
int in;
int ft;
cout << "Actual results : " << chain(chainTest,&ft,&in);
cout << " " << "feet: " << ft << " " << "inches: " << in << endl;
cout << endl << endl;
cout << "testing grow: " << endl;
cout << "test data 1: ";
showArray(testArray, size);
cout << endl;
cout << "Expected result: 1 1 2 2 3 3 4 4 5 5 6 6 7 7 8 8 " << endl;
cout << "Actual results: " << *(grow(testArray, size));
cout << endl << endl;
cout << "testing subArray:" << endl;
cout << "test data: ";
showArray(testArray, size);
cout << endl;
int start = 5;
int length = 3;
cout << "start: " << start << " " << "length: " << length << endl;
cout << "Expected result: " << "6 7 8" << endl;
cout << "Actual result: " << *(subArray(testArray, start, length));
cout << endl;
return 0;
}
Output:
As you notice, the loop is terminating after one traversal. The grow function is intended to duplicate and expand. In other words, it's supposed to make a copy of itself and append as it traverses. Any ideas as to why I am getting hung on the first element of the array?
You are actually doubling the array but only the first element is being printed because you are dereferencing an int* . To print all the elements, write a loop and print all the elements.
Also there is so much memory leak here. Please free memory after you are done using it. You are read about the delete[] operator.
Your loop going two at a time is good but it prevents you from selecting every element in the original array causing you to skip the even numbers. check your for loop and consider using two counters or if you want to modify your for loop to
for(int i = 0; i < size*2; i+=2){
*(newArray + i) = *(arr+i/2);
*(newArray + i + 1) = *(arr+i/2);
}
to ensure every element is reached
also as stated in the comments, use the showArray method you implemented
showArray(grow(testArray, size),size*2);
I am new to C++ and am trying to build a simple program that with the users input to proceed will generate a random left or right. I had the program working correctly until I added in the array to try and store each item as I have to output them as soon and the user would like to exit the loop. The program seems to compile fine but at run time I receive "Unhandled exception at 0x012B1CA9" Any help would be greatly appreciated.
#include <iostream>
#include <ctime>
using namespace std;
int main()
{
int userSelection = 1;
const int MAX = '100';
int randNum(0);
int one (0);
int two (0);
int total(0);
int sel[MAX];
do
{
cout << "Press 1 to pick a side or 0 to quit: ";
cin >> userSelection;
for (int i = 1; i < MAX; i++)
{
srand(time(NULL));
sel[i] = 1 + (rand() % 2);
if (sel[i] == 1)
{
cout << "<<<--- Left" << endl;
one++;
total++;
}
else
{
cout << "Right --->>>" << endl;
two++;
total++;
}
}
} while (userSelection == 1);
cout << "Replaying Selections" << endl;
for (int j = 0; j < MAX; j++)
{
cout << sel[j] << endl;
}
cout << "Printing Statistics" << endl;
double total1 = ((one / total)*100);
double total2 = ((two / total)*100);
cout << "Left: " << one << "-" << "(" << total1 << "%)" << endl;
cout << "Right: " << two << "-" << "(" << total2 << "%)" << endl;
system("pause");
return 0;
};
You have a multi-character constant here... and the behavior doesn't go as expected...
Change this line
const int MAX = '100';
to
const int MAX = 100;
Note the removed single quotes.
And secondly, I will advice you to remove the Seed of the C random generator from the for loop because, you'll likely get the same values from the rand() if you always call it immediately after seeding...
But preferable use the algorithm from C++'s random header
Here is a corrected version of your original code....
#include <iostream>
#include <ctime>
using namespace std;
int main()
{
int userSelection = 1;
const int MAX = 100; // <---changed
int randNum(0);
int one (0);
int two (0);
int total(0);
int sel[MAX];
do
{
cout << "Press 1 to pick a side or 0 to quit: ";
cin >> userSelection;
srand(time(NULL)); //< moved to here
for (int i = 0; i < MAX; i++) // <-- modified starting index
{
sel[i] = 1 + (rand() % 2);
if (sel[i] == 1)
{
cout << "<<<--- Left" << endl;
one++;
total++;
}
else
{
cout << "Right --->>>" << endl;
two++;
total++;
}
}
} while (userSelection == 1);
cout << "Replaying Selections" << endl;
for (int j = 0; j < MAX; j++)
{
cout << sel[j] << endl;
}
cout << "Printing Statistics" << endl;
double total1 = ((one / total)*100);
double total2 = ((two / total)*100);
cout << "Left: " << one << "-" << "(" << total1 << "%)" << endl;
cout << "Right: " << two << "-" << "(" << total2 << "%)" << endl;
system("pause");
return 0;
};
I think that it is basically good idea to read more about C data types and declaration. Your error:
const int MAX = '100' should be const int MAX = 100 without any quotes. C++ does implicit conversion from character literals to int.
#include <iostream>
#include <fstream>
#include <iomanip>
using namespace std;
int main(int argc, char *argv[]) {
ofstream outData;
ifstream inData;
string inString;
int matrix[12][12];
int rowSize, colSize;
inData.open("C:\\Users\\JSU\\Documents\\ArrayInput.txt");
inData >> rowSize >> colSize;
cout << "Row= " << rowSize << "\t Col= "<<colSize<< endl;
for (int r=0; r <rowSize; r++){
for (int c=0; c <colSize; c++){
inData >> matrix[r][c] ;
}
}
// print the input values
cout << "For the "<< rowSize << " x " << colSize << " array:"<<endl;
for (int r=0; r <rowSize; r++){
for (int c=0; c <colSize; c++){
cout << matrix[r][c] << " ";
}
cout<<endl;
}
cout << endl<<endl;
// find the largest in each row
for (int c=0; c <colSize; c++){
int largest = matrix[0][c]; //make the first cell value as the largest until you find otherwise
int smallest = matrix[0][c]; //make the first cell value as the smallest until you find otherwise
int sum=0;
for (int r=0; r <rowSize; r++){
if (matrix[r][c] > largest) //found a new larger value than the largest
largest = matrix[r][c];
if (matrix[r][c] < smallest) //found a new smaller value than the smallest
smallest = matrix[r][c];
sum = sum + matrix[r][c];
}
cout << "The sum of column "<< c + 1 << " is " << sum << endl;
cout << "The average of column "<< c + 1 << " is "<<fixed<<setprecision(2)<< (double)sum/rowSize << endl;
cout << "The largest value in column "<< c + 1 << " is " << largest << endl;
cout << "The smallest value in column "<< c + 1 << " is " << smallest << endl;
cout << "Is column " << c + 1 << " strictly ascending? " << endl;
cout<<endl;
}
inData.close();
return 0;
}
This is my code, and I've done almost everything of what I need. I just can't figure out how to cout the four corners of the array, and I need to print something that says cout << "Is column " << c + 1 << " strictly ascending? " << endl; and I can't figure out how to make that work.
Any and all help is appreciated.
Printing Matrix Corners
Here is how to print the four corners of a matrix.
Note that the corners are at: (0,0), (0, MAX_COLUMNS), (MAX_ROWS, 0) and (MAX_ROWS, MAX_COLUMNS).
const unsigned int MAX_ROWS = 12U;
const unsigned int MAX_COLS = 12U;
unsigned int matrix[MAX_ROWS][MAX_COLS];
//...
cout << matrix[0][0] << endl;
cout << matrix[MAX_ROWS][0] << endl;
cout << matrix[0][MAX_COLS] << endl;
cout << matrix[MAX_ROWS][MAX_COLS] << endl;
Ascending Column Values
By definition, a column has ascending values if column[n] < column[n + 1].
Implementing this in a for loop:
bool is_ascending = true;
for (unsigned int col = 0;
(col < MAX_COLS-1) && is_ascending;
++col)
{
if (matrix[row][col] >= matrix[row][col + 1])
{
is_ascending = false;
}
}
You may want to adjust the rule and let equal items count as ascending values.
The corners of an two dimensional array can be obtained as follows:
let an array a be = {1,2,3,4,5,6,7,8,9} Then the corner elements of the example array would be 1,3,7 and 9.
So, our Program would be like:-
#include<iostream>
using namespace std;
int main()
{
int a[][3]={1,2,3,4,5,6,7,8,9};
for(int i=0; i<3; i++){
for(int j=0; j<3; j++){
if(i%2==0||j%2==0)
cout << a[i][j];
else
cout << " ";
}
cout << endl;
}
return 0;
}
I'm working on an assignment for school. The code is supposed to read form a file and create an array, then sort the values of the array to output certain info. It works just fine as long as I have 3+ lines of info in the file. If not, I get the following error:
First-chance exception at 0x01305876 in Homework11.exe: 0xC0000005: Access violation reading location 0xcd71b288.
Unhandled exception at 0x01305876 in Homework11.exe: 0xC0000005: Access violation reading location 0xcd71b288.
I can't figure out why, any help would be appreciated. Here's the code:
#include <iostream> //calls the information needed
#include <iomanip>
#include <algorithm>
#include <fstream>
#include <string>
using namespace std; //sets all unmarked commands to std::
const int ARRSIZE = 1000;
struct Student
{
string firstName;
string lastName;
string id, temp;
double gpa;
};
int readArray(ifstream& ifile, Student arr[]);
void swapElements(Student arr[], int i, int j);
void sortArray(Student arr[], int numberInTheArray);
int main()
{ // Declares the needed variables
double sought, min, max;
int i, ival, returnvar, count = 0, mincount, maxcount;
string filename;
ifstream ifile;
Student arr[ARRSIZE];
cout << "Input File Name: ";//requesting the file name
cin >> filename;
ifile.open(filename.c_str());//opening the file
if (!ifile)//checking if it opened or not
{
cout << endl << "That file does not exist!" << endl;//informing the user it did
return 1;//not open and returning 1
}
cout << "Which number do you want to return? ";//requesting the desired number
cin >> ival;
i = ival - 1;
cout << endl;
returnvar = readArray(ifile, arr);
min = arr[0].gpa;
max = arr[0].gpa;
sought = arr[0].gpa;
while (count < returnvar)
{
if (arr[count].gpa < min)
{
min = arr[count].gpa;
mincount = count;
}
if (arr[count].gpa > max)
{
max = arr[count].gpa;
maxcount = count;
}
if (count == i)
{
sought = arr[count].gpa;
}
count++;
}
if (count == 0)
{
cout << "The file is empty!" << endl;
return 1;
}
cout << "Before Sort:" << endl;
cout << " Min GPA is " << min << " for " << arr[mincount].lastName << "." << endl;
cout << " Max GPA is " << max << " for " << arr[maxcount].lastName << "." << endl;
if (returnvar < ARRSIZE)
{
cout << " WARNING: Only " << returnvar << " numbers were read into the array!" << endl;
}
if (i >= returnvar)
{
cout << " There aren't that many numbers in the array!" << endl << endl;
}
else if (i > ARRSIZE)
{
cout << " " << i << " is bigger than " << ARRSIZE << "!" << endl << endl;
}
else if (i < returnvar)
{
cout << " Value " << ival << " is " << sought << " for " << arr[i].lastName << "." << endl << endl;
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
sortArray(arr, returnvar);
count = 0;
while (count < returnvar)
{
if (arr[count].gpa < min)
{
min = arr[count].gpa;
mincount = count;
}
if (arr[count].gpa > max)
{
max = arr[count].gpa;
maxcount = count;
}
if (count == i)
{
sought = arr[count].gpa;
}
count++;
}
cout << "After Sort:" << endl;
cout << " Array[0] GPA is " << min << " for " << arr[0].lastName << "." << endl;
cout << " Array[" << (returnvar - 1) << "] GPA is " << max << " for " << arr[(returnvar - 1)].lastName << "." << endl;
if (returnvar < ARRSIZE)
{
cout << " WARNING: Only " << returnvar << " numbers were read into the array!" << endl;
}
if (i >= returnvar)
{
cout << " There aren't that many numbers in the array!" << endl << endl;
}
else if (i > ARRSIZE)
{
cout << " " << i << " is bigger than " << ARRSIZE << "!" << endl << endl;
}
else if (i < returnvar)
{
cout << " Value " << ival << " is " << sought << " for " << arr[i].lastName << "." << endl << endl;
}
return 0;
}
int readArray(ifstream& ifile, Student arr[])
{
int counter = 0;
while ((ifile) && (counter <= ARRSIZE))
{
ifile >> arr[counter].firstName;
ifile >> arr[counter].lastName;
ifile >> arr[counter].id;
ifile >> arr[counter].gpa;
counter++;
}
return (counter - 1);
}
void sortArray(Student arr[], int numberInTheArray)
{
for (int i = 0 ; i < numberInTheArray - 1; i++)
{
for (int j = 0 ; j < numberInTheArray - 1; j++)
{
if ( arr[j].gpa > arr[j + 1].gpa)
{
swapElements(arr, j, j+1);
}
}
}
}
void swapElements(Student arr[], int i, int j)
{
Student temp;
temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
Please ignore the insanity and comments. Like I said, for an entry level course.
Try replacing counter <= ARRSIZE with counter < ARRSIZE (a rule of thumb in C is: never use <= in operations related to container sizes).
EDIT: also in your main(), you must check that i < ARRSIZE (equivalently, return error if i >= ARRSIZE). At present you seem to accept the case i == ARRSIZE, which is also wrong. And finally, readArray should return counter (that is, one more than the last written index).