Insertion Sort Initiation - c++

I am brand new to stack overflow here so thank you all for your patience in helping me with my issue. I am writing a program in C++ that implements the insertion sort by sorting numbers from a .txt file. It accepts a file, shows the contents and then asks the user if they want to sort the numbers. When I key "y" it is supposed to initiate the insertion sort algorithm in my code. However right now all it does is finish compiling. Any advice is greatly appreciated.
#include <iostream>
#include <fstream>
#include <string>
using namespace std;
//Read file input and display contents
ifstream& readfile(ifstream& file)
{
string line;
if (getline(file, line))
{
cout << line;
}
return file;
}
int main()
{
string fileName, line, r;
int n, i, j, k, temp;
int a[n];
ifstream fs;
cout << "enter file: ";
cin >> fileName;
ifstream file(fileName);
if (file.is_open())
{
while (readfile(file))
{
}
}
cout << endl << endl << "Sort File? y or n? ";
cin >> r;
if (r == "y")
{
for (i = 0; i < n; i++)
{
cin >> a[i];
}
for (i = 1; i < n; i++)
{
for (j = i; j >= 1; j--)
{
if (a[j] < a[j - 1])
{
temp = a[j];
a[j] = a[j - 1];
a[j - 1] = temp;
}
else
{
break;
}
}
}
for (k = 0; k < n; k++)
{
cout << a[k] << endl;
}
}
else
{
cout << endl << "error" << endl;
}
cin.get();
return 0;
}

n is not initialized.
for (i=0;i<n;i++)
{
cin >> a[i];
}
here nothing happen because (if your are lucky...) n=0.
Initialize n to 5 if you want only 5 entries.
or
use STL containers like std::vector for example, you are using C like language here...
Change your end condition in your loop when users initialize insertion
For example if user insert "stop" word:
std::vector<int> vIntegers;
std::string input;
int n = 0;
while ( input != "stop")
{
std::cin >> input;
// test if integer here
{
vIntegers.push_back(n);
}
}
here the post to test if a string is an integer
How do I check if a C++ string is an int?

Related

c++ Faliure on vector at runtime: vector subscript out of range

im gettin this really annoying error message. I know Im only new to this but it seems the type of thing I could figure out. Can anyone show me where im going wrong please?
The message at run time is: Debug Assertion Failed! Program: .... File: c:\program files\microsoft visual studio 10.0\vc\include\vector Line: 932 Expression: Vector subscript out of range
and the code is
#include<iostream>
#include<vector>
using namespace std;
struct Things {
string name;
string color;
string poison;
string burns;
double height;
};
typedef vector<Things> Forest;
void read_data(Forest& v) {
int n;
cin >> n;
for (int i = 0; i < n; ++i) {
cout << "DINTRE" << endl;
cin >> v[i].name;
cout << v[i].name << endl;
}
}
int count(const Forest& v, string name, string color, string poison, string burns, double height) {
int x = v.size();
int cont = 0;
for (int i = 0; i < x; ++i) {
if (v[i].name == name or name == "*") {
if (v[i].color == color or color == "*") {
if (v[i].poison == poison or poison == "*") {
if (v[i].burns == burns or burns == "*") {
if (v[i].height >= height or height == 0) ++cont;
}
}
}
}
}
return cont;
}
int main() {
Forest v;
read_data(v);
vector<string> pregunta(4);
while (cin >> pregunta[0]) {
for (int i = 1; i < 4; ++i) {
cin >> pregunta[i];
}
double height;
cin >> height;
cout << count(v, pregunta[0], pregunta[1], pregunta[2], pregunta[3], height) << endl;
}
}
consider the first line that tries to modify the data in v:
cin >> v[i].name;
This is occurring while v is an empty vector (has a size of 0). To add elements to the end of a vector you need to use push_back:
string name;
cin >> name;
v.push_back(name);
the square brackets ("[]") are for accessing an element that already exists in the vector.
In read_data you access the std::vector<Things> (Forest) v out of bounds (out of range) since the vector is empty.
You could resize it after having asked the user for how many elements that should be entered.
Example:
void read_data(Forest& v) {
int n;
if(std::cin >> n && n > 0) v.resize(n); // resize
for (int i = 0; i < v.size(); ++i) { // use v.size() here
std::cout << "DINTRE\n";
std::cin >> v[i].name;
std::cout << v[i].name << '\n';
}
}
or simpler by using a range-based for loop:
void read_data(Forest& v) {
int n;
if(std::cin >> n && n > 0) v.resize(n);
for(auto& thing : v) {
std::cout << "DINTRE\n";
std::cin >> thing.name;
std::cout << thing.name << '\n';
}
}
The size of vector, passed in read_data(), is 0 i.e. it's an empty vector. In read_data(), when you doing v[i] that means you are trying to access ith element of vector v which does not exists. Hence, you are getting the error. To fix this, create an object of type Things, take user input and push_back() it in vector v:
for (int i = 0; i < n; ++i) {
Things x;
cout << "DINTRE" << endl;
cin >> x.name;
cout << x.name << endl;
v.push_back(x);
}

Pushing back a vector gives absurd results (C++)

Hello so I've seen some other posts about it but they never seem to solve my issue, or I just can't understand it with my peanut sized brain.
If I input something, and push it back to the vector, it would always have some stupidly absurd number(s)
For those who want context or in case it's outside of what I think is the problem, here's the full code:
#include <iostream>
#include <string>
#include <array>
#include <algorithm>
#include <vector>
using namespace std;
void stringToVec(string input, vector<int> output)
{
int e = 0;
string temp;
//cout << "size: " << input.size() << '\n';
for(int i = 0; i < input.size(); i++)
{
if(input[i] != ' ')
{
temp += input[i];
}
else if(input[i] == ' ')
{
int num = stoi(temp);
output.push_back(num);
temp = ""; // clear temp
}
}
}
int main()
{
int a, b;
string numsIn1, numsIn2;
cin >> a;
cin >> ws;
getline(cin, numsIn1);
numsIn1 += ' ';
int nums1[a];
// =======================
cin >> b;
cin >> ws;
getline(cin, numsIn2);
numsIn2 += ' ';
int nums2[b];
// =======================
vector<int> output;
stringToVec(numsIn1, output);
stringToVec(numsIn2, output);
int e = 0;
for(int i = 0; i < a; i++)
{
output.push_back(nums1[i]);
}
for(int i = 0; i < b; i++)
{
output.push_back(nums2[i]);
}
sort(output.begin(), output.end());
//int dyfslashj[3] = {3, 2, 1};
for(int i = 0; i < a + b; i++)
{
cout << output[i] << ' ';
}
return 0;
}
Here's the line thats most likely to be the problem. For example if I input the number "3 4 2" the vector would be like "5234523452345 32452 34523", or some absurd value
void stringToVec(string input, vector<int> output)
{
int e = 0;
string temp;
//cout << "size: " << input.size() << '\n';
for(int i = 0; i < input.size(); i++)
{
if(input[i] != ' ')
{
temp += input[i];
}
else if(input[i] == ' ')
{
int num = stoi(temp);
output.push_back(num);
temp = ""; // clear temp
}
}
}
maybe there are something wrong with your "cin". I can see you used cin and getline. But getline will read at the first line.No matter it have been "cin".you can try to use some strings as parameter to the function to see whether it's correct or not

Printing the searched line

I want to search for a name from a list of names and if its found I should return the whole info of that person else not found. I dont know why my code is not working. I can print the info of the person, eg:
Input:
3
Steve 9812761810 017
Wayne 8299915781 102
Ronnie 9161462903 120
Wayne
Output:
Wayne 8299915781 102
#include <iostream>
#include <string.h>
using namespace std;
int main() {
string name[100];
long long number[100];
int year[100], i, n, check = 0;
string inp;
cin >> n;
for (i = 0; i < n; i++) {
cin >> name[i] >> number[i] >> year[i];
}
cin >> inp;
for (i = 0; i < n; i++) {
if (inp == name[i]) {
check = 1;
}
}
if (check == 0)
cout << "Info Not found";
else
cout << "The Entered Name is found";
for (i = 0; i < n; i++)
cout << name[i] << number[i] << year[i];
return 0;
}
After reading an integer from the input stream, you should use cin.ignore(); before reading any strings from the input stream.
cin.ignore(); ignores the "new line" character.
Your modified code:
#include <iostream>
#include <string.h>
using namespace std;
int main() {
string name[100];
long long number[100];
int year[100], i, n, check = 0;
string inp;
cin >> n;
cin.ignore();
for (i = 0; i < n; i++) {
cin >> name[i] >> number[i] >> year[i];
cin.ignore();
}
cin >> inp;
for (i = 0; i < n; i++) {
if (inp == name[i]) {
check = 1;
}
}
if (check == 0)
cout << "Info Not found";
else
cout << "The Entered Name is found";
for (i = 0; i < n; i++)
cout << name[i] << number[i] << year[i];
return 0;
}
Read more here: Using getline(cin, s) after cin
At the end of the program, you are ignoring the value of check and just printing everything in your list regardless of whether the entered name was actually found or not.
Try something more like this instead:
#include <iostream>
#include <string>
using namespace std;
int main() {
string name[100];
long long number[100];
int year[100], i, n, idx = -1;
string inp;
cin >> n;
for (i = 0; i < n; i++) {
cin >> name[i] >> number[i] >> year[i];
}
cin >> inp;
for (i = 0; i < n; i++) {
if (inp == name[i]) {
idx = i;
break;
}
}
if (idx == -1)
cout << "Info Not found";
else {
cout << "The Entered Name is found: ";
cout << name[idx] << " " << number[idx] << " " << year[idx];
}
return 0;
}
You might also consider using a struct to organize your data better, eg:
#include <iostream>
#include <string>
using namespace std;
struct myData {
string name;
long long number;
int year;
};
istream& operator>>(istream &is, myData &data) {
is >> data.name >> data.number >> data.year;
return is;
}
ostream& operator<<(ostream &os, const myData &data) {
os << data.name << " " << data.number << " " << data.year;
return os;
}
int main() {
myData data[100];
int i, n, idx = -1;
string inp;
cin >> n;
for (i = 0; i < n; i++) {
cin >> data[i];
}
cin >> inp;
for (i = 0; i < n; i++) {
if (inp == data[i].name) {
idx = i;
break;
}
}
if (idx == -1)
cout << "Info Not found";
else
cout << "The Entered Name is found: " << data[idx];
return 0;
}

Controlling input in c++ and display

Question :
Your program is to use the brute-force approach in order to find the Answer to Life, the Universe, and Everything. More precisely... rewrite small numbers from input to output. Stop processing input after reading in the number 42. All numbers at input are integers of one or two digits.
Example
Input:
1
2
88
42
99
Output:
1
2
88
So that is the question, however i am still a beginner and unable to have an input tab like that. In my program, how should i modify it such that it still accepts numbers after 42, however, it does not print them? currently I am only able to terminate the input at 42.
#include <iostream>
using namespace std;
int main()
{
int A[100], num, i=0,k,count;
for(count = 0; count != 1;){
cin >> k;
if (k!=42){
A[i] = k;
i++;
}
else
count =1;
}
cout << endl;
for (count = 0; count <i; count ++){
cout << A[count] << endl;
}
}
You don't have to use array at all. You can print the value just after reading it. Exit when you read 42. This may help you.
#include <iostream>
using namespace std;
int main() {
// your code goes here
int n ;
for(; ;) {
cin >> n ;
if(n == 42) {
return 0 ;
}
cout << n << endl ;
}
return 0;
}
Pretty sure the easiest way to do so is to simply ask the user how many numbers they need to enter.
#include <iostream>
using namespace std;
int main()
{
int A[100], k, count;
cout << "How many numbers do you want to enter ? ";
cin >> count; //this is to count how many numbers the user wants to enter
for(int i(0); i < count; ++i) //put all the numbers user enters in your array
{
cin >> k;
A[i] = k;
}
cout << endl;
for (int i(0); i < count; ++i)
{
if (A[i] == 42) //if the element at index i is == 42 then stop displaying the elements
break;
else
cout << A[i] << " "; //else display the element
}
cout << endl;
return 0;
}
Else you would need to put everything in a string and parse it and i'm not quite sure how that goes as I am a beginner as well.
EDIT:
Actually here you go, I think that is correct and does exactly what you want.
Do keep in mind that if user enters p.e "1 88 442" it will output "1 88 4" because it found "42" in "442". But it should be okay because you precised input numbers should only be two digits max.
#include <iostream>
using namespace std;
int main()
{
string k;
getline(cin, k);
cout << endl;
for (unsigned int i(0); i < k.length(); ++i)
{
if (!((k[i] == '4') && (k[i+1] == '2'))) //if NOT 4 followed by 2 then display
cout << k[i];
else
break; //else gtfo
}
cout << endl;
return 0;
}
Use a bool value to control the execution of your code.
#include <iostream>
#define N_INPUT 100
#define THE_ANSWER 42
using namespace std;
int main()
{
int array[N_INPUT], i, input, count=0;
bool universeAnswered = false;
for (i = 0; i < N_INPUT; i++) {
cin >> input;
if (!universeAnswered)
{
if (input == THE_ANSWER) {
universeAnswered = true;
} else {
array[count] = input;
count++;
}
}
}
for (i = 0; i < count; i++) {
cout << array[i] << endl;
}
}
(My code was not tested)
You just have to have some state to see if you have seen 42 already, and only output if you haven't
#include <iostream>
int main()
{
bool output = true;
for (int n; std::cin >> n;)
{
output &= (n != 42);
if (output)
{
std::cout << n << std::endl;
}
}
return 0;
}

How to input test case in c++ code in google code jam

I tried solving a problem in the Google Code Jam Practice Page Minimum Scalar Product and i have the program written in c++ and i read in the FAQ page that we have to test our programs with the .in test file placed on the practice page for download but i don't know how and i use UBUNTU 12.04 LTS & please i am participating in the contest for the first time..So any help would be greatly appreciated..Thanks In Advance
I tried
#include <vector>
#include <algorithm>
#include <iostream>
using namespace std;
int main()
{
int numCase;
cin >> numCase;
int i, j, n;
long long c;
for (i = 0; i < numCase; i++)
{
cin >> n;
vector<long long> array1, array2;
for (j = 0; j < n; j++)
{
cin >> c;
array1.push_back(c);
}
for (j = 0; j < n; j++)
{
cin >> c;
array2.push_back(c);
}
sort(array1.begin(), array1.end());
sort(array2.begin(), array2.end(), greater<long long>());
long long ans = 0;
for (j = 0; j < n; j++)
ans += (array1[j] * array2[j]);
cout << "Case #" << (i+1) << ": " << ans << endl;
}
return 0;
}
You can use ifstream and ofstream
as follows:
#include <vector>
#include <algorithm>
#include <iostream>
#include <fstream>
using namespace std;
int main()
{
ifstream fin("input.in");
ofstream fout("output.out");
//-- check if the files were opened successfully
if (!fin.is_open()) cout << "input.in was not open successfully" << endl;
if (!fout.is_open()) cout << "output.out was not open successfully" << endl;
int numCase;
fin >> numCase;
int i, j, n;
long long c;
for (i = 0; i < numCase; i++)
{
fin >> n;
vector<long long> array1, array2;
for (j = 0; j < n; j++)
{
fin >> c;
array1.push_back(c);
}
for (j = 0; j < n; j++)
{
fin >> c;
array2.push_back(c);
}
sort(array1.begin(), array1.end());
sort(array2.begin(), array2.end(), greater<long long>());
long long ans = 0;
for (j = 0; j < n; j++)
ans += (array1[j] * array2[j]);
fout << "Case #" << (i + 1) << ": " << ans << endl;
}
fin.close();
fout.close();
return 0;
}
You can treat fin and fout as cin, so instead of reading the input from the console, you read the input from the file in.txt. Instead of writing to the console using cout you write to output.out using fout.
The general format for test cases are:
int t;
cin >> t;
while (t--) (
{
//code here
}
So we make a variable for our test cases and ask the user to input a value for it... then we make a while loop which checks if the value of t > 0 and decrements the value by 1 every time)
Hope I helped! :D