How to discard extra inputs in a line c++ - c++

I am a novice in C++. I am trying to get input from the user for inserting in a multidimensional vector. The code works fine. But when I give extra inputs in the same line, my program does not disregard it and considers it in the next iteration.
For example when I give input in the following format:
m=3 n=4
1 2 3 4 5
1 3 5 5
1 345 65 567
the output is
1 2 3 4
5 1 3 5
5 1 345 65
But what the output I want is
1 2 3 4
1 3 5 5
1 345 67 567
int main() {
vector<vector<int>> vec;
int m, n, dat;
cout << "Enter dimensions of Vector";
cin >> m >> n;
// takes data n times into a subvector temp and inserts it into the vector vec m
// times
cout << "Enter elements one row at a time";
for(int i = 0; i < m; ++i) {
vector<int> temp;
for(int j = 0; j < n; ++j) {
cin >> dat;
temp.push_back(dat);
}
vec.push_back(temp);
}
for(int k = 0; k < vec.size(); ++k) {
for(int i = 0; i < vec[k].size(); ++i) {
cout << setw(4) << vec[k][i];
}
cout << endl;
}
}

Consider using std::getline to read a complete line. You can then use that to populate a std::istringstream that you then use to extract the exact number of elements you want. Also note:
Why is “using namespace std;” considered bad practice?
Example:
#include <iomanip>
#include <iostream>
#include <sstream>
#include <string>
#include <vector>
int main() {
std::vector<std::vector<int>> vec;
int m, n, dat;
std::cout << "Enter dimensions of Vector";
std::cin >> m >> n;
std::cin.ignore(); // skip newline
// takes data n times into a subvector temp and inserts it into the vector vec m
// times
std::cout << "Enter elements one row at a time\n";
for(int i = 0; i < m; ++i) {
std::string line;
std::vector<int> temp;
std::cout << " row " << (i + 1) << ": ";
std::getline(std::cin, line);
std::istringstream iss(line);
for(int j = 0; j < n; ++j) {
iss >> dat;
temp.push_back(dat);
}
vec.push_back(temp);
}
for(const auto& row : vec) {
for(int colval : row) {
std::cout << std::setw(4) << colval;
}
std::cout << "\n";
}
}

Related

Checking for duplicates in an array using for loop

I am trying to check whether there is any duplicate integer in the user input array. The problem is that the validation of the duplicate does not work properly and I have no idea why it is not showing the desired output. Following is the code:
#include <iostream>
using namespace std;
int main()
{
int length;
int arrValue;
cout << "Enter the length : ";
cin >> length;
int *arr = new int[length];
cout << "Enter " << length << " integers for array : ";
for(int i = 0; i < length; i++)
{
cin >> arr[i];
}
cout << "Array : ";
for(int i = 0; i < length; i++)
{
arrValue = arr[i];
for(int k = i + 1; k < length; k++)
{
if(arr[i] == arr[k])
{
cout << "Duplicate found" << endl;
break;
}
else
{
cout << arrValue << " ";
}
}
}
delete[] arr;
}
Current result (assuming no duplicate in user input):
Enter the length: 5
Enter 5 integers for array : 5 4 3 2 1
Array : 5 5 5 5 4 4 4 3 3 2
Expected result (assuming no duplicate in user input):
Enter the length: 5
Enter 5 integers for array : 5 4 3 2 1
Array : 5 4 3 2 1
Current result (assuming duplicate in user input):
Enter the length: 5
Enter 5 integers for array : 5 4 4 2 1
Array : 5 5 5 5 Duplicate found 4 4 3
Expected result (assuming duplicate in user input):
Enter the length: 5
Enter 5 integers for array : 5 4 4 2 1
Array : Duplicate found
I believe my loops is the source to the problem. The current result output 10 times and I do not understand why there will be so many same numbers appearing.
Do note that I am trying to apply the validation using loop only and not from C++ standard library.
The issue in your code is that you are printing out each array element every time a particular element is not matching another element. It seems that you only want to print out whether any duplicate values are found. For this, you can use a bool flag to indicate whether any element is duplicated:
bool found_dup = false;
for(int i = 0; i < length; i++)
for(int k = i + 1; k < length; k++)
if(arr[i] == arr[k])
{
found_dup = true;
break;
}
// else: don't print anything yet
and then at the end print out the array:
if (found_dup)
std::cout << "Duplicate found";
else
for(int i = 0; i < length; i++)
std::cout << arr[i] << " ";
You may achieve the program in a more enhanced way (where you don't need to define the length manually - notice the explanation given as comments in code):
#include <iostream> // for input/output operation
#include <vector> // for dynamic array management
#include <sstream> // to split the user inputs and assign them to the vector
#include <algorithm> // to sort the vector
#include <string> // to work with getline()
// using this statement isn't recommended, but for sake of simplicity
// and avoiding the use of std:: everywhere temporarily (for small programs)
using namespace std;
int main(void) {
vector<int> numbers;
vector<int> duplicates;
string input;
int temp;
// getting the user input as string
cout << "Enter the numbers: ";
getline(cin, input);
stringstream ss(input);
// splitting the user input string into integers and assigning
// them into the vector
while (ss >> temp)
numbers.push_back(temp);
// sorting the vector in increasing order
sort(numbers.begin(), numbers.end());
// getting the unique numbers (which are not repeated)
cout << "Unique numbers: ";
for (size_t i = 0, len = numbers.size(); i < len; i++) {
if (temp == numbers[i])
// if found a duplicate, then push into the 'duplicates' vector
duplicates.push_back(temp);
else
cout << numbers[i] << ' ';
temp = numbers[i];
}
// getting the duplicates
cout << "Total duplicates: ";
for (size_t i = 0, len = duplicates.size(); i < len; i++)
cout << duplicates[i] << ' ';
cout << endl;
return 0;
}
It'll output something like:
Enter the numbers: 1 4 8 9 3 2 3 3 2 1 4 8
Unique numbers: 1 2 3 4 8 9
Total duplicates: 1 2 3 3 4 8
Please change the if condition to something like this.
cout << "Enter the length : ";
cin >> length;
int *arr = new int[length];
cout << "Enter " << length << " integers for array : ";
for(int i = 0; i < length; i++)
{
cin >> arr[i];
}
cout << "Array : ";
for(int i = 0; i < length; i++)
{
arrValue = arr[i];
for(int k = i + 1; k < length; k++)
{
if(arrValue == arr[k]) //change here.
{
cout << "Duplicate found" << endl;
break;
}
else
{
cout << arrValue << " ";
}
}
}
delete[] arr;
}
I would also suggest to use a map data structure. Map allows you to count the frequency of numbers, and thus detect duplicates in linear time.
map<int, int> m; // specify the key-value data-type.
for(int i = 0;i<length;i++)
{
m[arr[i]]++;
}
map<int, int>::iterator it; // an iterator to iterate over the datastructure.
for(it = m.begin();it!=m.end();it++)
{
if(it->second>1) //it->second refers to the value(here, count).
{
cout<<it->first<<" "; //it->first refers to the key.
}
}
Your loops are actually iterating n-1 times for first element, n-2 times for second element etc., where n is the length of your array. This is why for 5 element array you have printed 5 4 times.
But generally, if the purpose is to detect duplicates in the array, this strategy is not the best one. Please note that having exemplary array 4 3 4, with current approach you will correctly detect for the first 4 that the third element is also 4 but once you will move to the third element, it will be marked as ok since it is not checked with the first one element.
You may consider another strategy: create another array of the n size. Then iterate through your original array and for each element check if that element is already in the new array. If you detect the presence, you may raise duplicate event. Otherwise you can add this element to the array.
It doesn't work because you're trying to print the same value everytime you find a different one. I got here a solution with one more array that will store the array. It would work too with just one array.
#include <iostream>
using namespace std;
int main()
{
int length;
int arrValue;
cout << "Enter the length : ";
cin >> length;
int *arr = new int[length];
int *noDuplicateArr = new int[length];
cout << "Enter " << length << " integers for array : ";
for(int i = 0; i < length; i++)
cin >> arr[i];
cout << "Array : ";
bool duplicateFound = false;
int noDuplicateArrLen = 0;
for(int i = 0; i < length && !duplicateFound; i++)
{
arrValue = arr[i];
int k;
for(k = i + 1; k < length; k++)
{
if(arrValue == arr[k])
{
duplicateFound = true;
break;
}
}
if (k == length)
noDuplicateArr[noDuplicateArrLen++] = arrValue;
}
if (duplicateFound)
{
cout << "Duplicate found";
}
else
{
for (int i = 0; i < noDuplicateArrLen; i++)
{
cout << noDuplicateArr[i] << " ";
}
}
delete[] arr;
delete[] noDuplicateArr;
}
Here is the version with just one array:
#include <iostream>
using namespace std;
int main()
{
int length;
int arrValue;
cout << "Enter the length : ";
cin >> length;
int *arr = new int[length];
cout << "Enter " << length << " integers for array : ";
for(int i = 0; i < length; i++)
cin >> arr[i];
cout << "Array : ";
bool duplicateFound = false;
int noDuplicateArrLen = 0;
for(int i = 0; i < length && !duplicateFound; i++)
{
arrValue = arr[i];
int k;
for(k = i + 1; k < length; k++)
{
if(arrValue == arr[k])
{
duplicateFound = true;
break;
}
}
if (k == length)
arr[noDuplicateArrLen++] = arrValue;
}
if (duplicateFound)
{
cout << "Duplicate found";
}
else
{
for (int i = 0; i < noDuplicateArrLen; i++)
{
cout << arr[i] << " ";
}
}
delete[] arr;
}

Read everything up to a whitespace from a text file

(C++) I've created a function to open the text file and assign the contents to an array. The first 2 elements in the array are the size of the grid. However, if either or both of the first 2 numbers are double digits, it doesnt read them in as double digits. Is there any way of doing this?
int openMap()
{
std::string fileName;
std::cout << "Please enter the file name with extension that you want to open: ";
std::cin >> fileName;
system("CLS");
std::ifstream file(fileName); //OPENS MAP FILE
int tmp;
int i = 0;
if (!file.is_open()) //CHECKS IF THE MAP FILE HAS OPENED CORRECTLY
{
std::cout << "Error Occured!\nCould not open file.";
return 0;
}
while (!file.eof()) //READS THE MAP FILE AND PASSES THE INFORMATION INTO AN ARRAY
{
file >> tmp;
checkNumber(tmp);
if (valid == true) //IF THE CHARACTER IS NOT A NUMBER THEN IT WONT BE PASSED INTO THE ARRAY
{
tmpArray[i] = tmp;
i++;
valid = false;
}
row = tmpArray[1]; //ASSIGNS THE FIRST 2 NUMBERS OF THE MAP FILE TO ROW AND COL VARIABLES
col = tmpArray[0];
}
return row, col;
}
I would assume I have to rewrite
file >> tmp
in some sort of different way, but not sure how.
Is there a way to scan through the text file until it hits a whitespace?
The text file contents looks like this
6 4 0 0 1 0 0 0 2 0 1 0 1 1 0 0 1 0 0 0 0 0 0 0 3 0
(the 6 or 4 or both can be double digits instead)
Edit:
for (int j = 0; j < row; j++)
{
for (int k = 0; k < col; k++)
{
_map[j][k] = tmpArray[l];
std::cout << _map[j][k] << " ";
l++;
}
}
There's quite a number of bugs in the code, you should probably use a debugger to step through and identify which parts of your program don't behave as expected.
while(!file.eof())
file >> tmp;
checkNumber(tmp);
if (valid == true) //IF THE CHARACTER IS NOT A NUMBER THEN IT WONT BE PASSED INTO THE ARRAY
{
tmpArray[i] = tmp;
i++;
valid = false;
}
row = tmpArray[1]; //ASSIGNS THE FIRST 2 NUMBERS OF THE MAP FILE TO ROW AND COL VARIABLES
col = tmpArray[0];
You set row=tmpArray[1] and col = tmpArray[0] every iteration of the loop which is not only unnecessary but also incorrect, especially since row=tmpArray[1] is being executed at i=0 when nothing has been placed in tmpArray[1] yet.
EDIT: This is a lot smaller, less error prone due to less variables and type conversions, and easier to read:
int row,col;
//Add error checking here
cin >> col;
cin >> row;
cout << "Cols: " << col << " Rows: " << row << endl;
vector<vector<int> >_map(row, vector<int>(col,0));
for(int j=0; j < row; j++)
{
for(int k=0; k < col; k++)
{
int tmp;
cin >> tmp;
//Add error checking for tmp
_map[j][k] = tmp;
cout << _map[j][k] << endl;
}
}
There are some problems with your code. First the return type of your function is int but you are returning multiple values. Here is a complete running code which should solve your problem.
#include <iostream>
#include <fstream>
#include <vector>
std::vector< std::vector<int> > openMap() {
std::string fileName;
std::cout << "Please enter the file name with extension that you want to open: ";
std::cin >> fileName;
std::fstream myfile(fileName, std::ios_base::in);
int row, col;
myfile >> row;
myfile >> col;
int a;
std::vector< std::vector<int> > retval;
for (int i = 0; i < row; i++) {
std::vector<int> v1;
for (int j = 0; j < col; j++) {
myfile >> a;
v1.push_back(a);
}
retval.push_back(v1);
}
return retval;
}
int main(int argc, char * argv[])
{
std::vector< std::vector<int> > _map = openMap();
for(int i = 0; i < _map.size(); i++) {
for (int j = 0; j < _map[i].size(); j++) {
std::cout << _map[i][j] << " ";
}
std::cout << std::endl;
}
return 0;
}
I guess that not so many people will be interested. But please see below a possible solution to your problem.
The code uses modern C++ algorithms.
It is very simple and straightforward.
#include <iostream>
#include <fstream>
#include <vector>
#include <iterator>
#include <algorithm>
int main() {
// Ask user, to give a filename
std::cout << "Please enter the file name with extension that you want to open: ";
// Get the filename from the user
if (std::string fileName; std::cin >> fileName) {
// Open the file and check, if it is open
if (std::ifstream sourceFile(fileName); sourceFile) {
// Read the number of rows and columns of the matrix
if (size_t numberOfColumns, numberOfRows; sourceFile >> numberOfColumns >> numberOfRows) {
// Create a matrix with the given number of rows and columns
std::vector<std::vector<int>> result(numberOfRows, std::vector<int>(numberOfColumns, 0));
// Read data from the input stream and put it into the matrix
for (size_t i = 0; i < numberOfRows; ++i) {
std::copy_n(std::istream_iterator<int>(sourceFile), numberOfColumns, result[i].begin());
}
// Print result. Go through all lines and then copy line elements to std::cout
std::for_each(result.begin(), result.end(), [](std::vector<int>& c) {
std::copy(c.begin(), c.end(), std::ostream_iterator<int>(std::cout, " ")); std::cout << "\n"; });
}
}
else {
std::cerr << "\n*** Error: Could not open source File\n\n";
}
}
return 0;
}

pointers with numbers in backwards [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 4 years ago.
Improve this question
I need to receive an undetermined number of integer numbers in between (0-9). With this numbers, print them forwards and backwards, and then erase the numbers at the corners.
Example:
3 5 1 9 4 6 2 4 4 2 6 4 9 1 5 3
5 1 9 4 6 2 4 4 2 6 4 9 1 5
1 9 4 6 2 4 4 2 6 4 9 1
9 4 6 2 4 4 2 6 4 9
4 6 2 4 4 2 6 4
6 2 4 4 2 6
2 4 4 2
4 4
And here is the code I have so far:
#include <iostream>
using namespace std;
int a;
int p;
int set;
void numberss()
{
for set[](int a=0; a<p; a++)
}
int main()
{
cin >> p;
cin >> a;
const int SIZE = p;
int set[] = {a};
int *numPtr;
numPtr = set;
for (int index = 0; index < SIZE; index++)
{
cout << *numPtr << " ";
numPtr++;
}
for (int index = 0; index < SIZE; index++)
{
numPtr--;
cout << *numPtr << " ";
}
return 0;
}
If we ignore errors, you can read the numbers in one at a time, and form a string for the first line of output. Forming the string will involve appending a reversed copy to the original. Once the string is formed, you can output that string for the first line. Then replace the first number with a space character, and shrink the string from the back by two characters. Keep doing that until you are done.
This works because the numbers are all single digit.
int main (void)
{
int N;
std::string nums;
std::cin >> N;
for (int i = 0, x; i < N; ++i) {
std::cin >> x;
nums += std::to_string(x) + ' ';
}
nums.append(nums.rbegin() + 1, nums.rend());
for (int i = 0; i < N; ++i) {
std::cout << nums << '\n';
nums[2*i] = ' ';
nums.resize(nums.size()-2);
}
}
DEMO
Your code doesn't work because you are not reading all of the numbers from the user's input, you are only reading the count and the 1st number. Also, you are not looping enough times to output the numbers in a triangular fashion, you are only outputting the 1st line of the triangle.
Try this instead:
#include <iostream>
#include <vector>
using namespace std;
int main()
{
int p;
vector<int> set;
cin >> p;
set.resize(p);
for (int i = 0; i < p; ++i)
cin >> set[i];
for (int index = 0; index < p; index++)
{
int *numPtr = &set[index];
for (int i = 0; i < index; ++i)
cout << " ";
for (int i = index; i < p; ++i)
cout << *numPtr++ << " ";
for (int i = index; i < p; i++)
cout << *--numPtr << " ";
cout << endl;
}
return 0;
}
Live Demo
That being said, here is an alternative approach that is more C++-ish and less C-ish, by using iterators instead of pointers, and using STL algorithms. Also, you should always validate user input before using it:
#include <iostream>
#include <vector>
#include <iomanip>
#include <algorithm>
#include <limits>
#include <iterator>
#include <cstdint>
using uint16vec = std::vector<uint16_t>; // there is no operator>> for uint8_t...
int main()
{
size_t count = 0;
std::cin >> count;
uint16vec set;
set.reserve(count);
for (size_t i = 0; i < count; ++i)
{
uint16vec::value_type num;
while (!((std::cin >> num) && (num <= 9)))
{
std::cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
std::cin.clear();
std::cout << "Enter a valid number 0..9!" << std::endl;
}
set.push_back(num);
}
auto begin = set.begin(), end = set.end();
auto rbegin = set.rbegin(), rend = set.rend();
auto out = std::ostream_iterator<uint16vec::value_type>(std::cout, " ");
std::cout << std::setfill(' ');
for (size_t i = 0; i < count; ++i)
{
std::cout << std::setw((i*2)+1);
std::copy(begin++, end, out);
std::copy(rbegin, rend--, out);
std::cout << std::endl;
}
return 0;
}
Live Demo
Give this a shot, mate. I've commented it so you can follow along. It allows for characters other than numbers because that seemingly wasn't a requirement of your assignment, so it's on you to sort and filter those out. It prints as intended, so here's hoping that this is what you're looking for to start off with your search for the right answer.
#include <iostream>
#include <vector>
#include <string>
using namespace std;
void pop_front(vector<char>& _vector)
{
_vector.front() = move(_vector.back());
_vector.pop_back();
}
int main()
{
vector<char> characterList;
string consoleInput;
cin >> consoleInput;
//Initialize by pushing everyting from the console into our vector.
for (char c : consoleInput)
{
characterList.push_back(c);
}
//After adding from the console, now we'll do it in reverse.
for (int i = consoleInput.length() - 1; i > -1; i--)
{
characterList.push_back(consoleInput[i]);
}
//Print where we are currently up to for display purposes.
for (char c : characterList)
{
cout << c;
}
// Newline.
cout << "\n";
//Now let's start to chop it down. It'll take the same iterations as the console input, because we're doubling down.
for (int i = 0; i < consoleInput.length() - 1; i++)
{
characterList.erase(characterList.begin());
characterList.pop_back();
for (char c : characterList)
{
cout << c;
}
cout << "\n";
}
return 0;
}

Moving elements in an array by certain amount

So I have a program that reads in a certain number of keys. An example would be
5 1 10 21 9 6 21 11 13 16 20
The text file example would be
Java 2 linux 3 fear 0 pool 2 do 0 red 1 lock. 1 I 0 random 2
I want my program to start at Java and depending on first key, which in this case is 5, would move over 5 elements leading to "red". And so on and so on. However, I have managed to read in all the data and put them into arrays, I am just having trouble figuring out how to move the pointer in the array.
Code:
#include <iostream>
#include <fstream>
using namespace std;
struct pieces {
char word[5];
int jump;
} ;
// Main Function
int main ()
{
// declare variables
int wordCount[2];
int keyCount[2];
int numKeys, numKeys2;
int numWords;
int keyAmount = 1;
int wordAmount = 23;
int keyarr[11];
pieces cypher[wordAmount];
char filename[10];
ifstream inData;
int temp[10];
//prompt user for input file
cout << " Enter file name: ";
cin >> filename;
inData.open(filename);
if(inData.is_open());
{
// read in data
for ( numKeys = numWords = 0; numKeys < keyAmount; numKeys++){
// read in num of words and keys
inData >> wordCount[numKeys] >> keyCount[numKeys];
//read in words followed by jump key
for( numWords = 0; numWords < wordAmount; numWords++){
inData >> cypher[numWords].word >> cypher[numWords].jump;
}
// read in the actual keys
for( numKeys2 = 0; numKeys2 < wordCount[numKeys]; numKeys2++){
inData >> keyarr[numKeys2];
}
}
//print out data
for( int j = 0; j < numKeys; j++){
cout << wordCount[j] << "\n";
cout << keyCount[j] << "\n";
}
cout << "\n";
for ( int i = 0; i < wordAmount; ++i){
cout << cypher[i].word << " ";
cout << cypher[i].jump << " ";
}
cout << "\nKeys: " << "\n";
for(int k = 0; k < 11; k++){
cout << keyarr[k] << " ";
}
cout << "\n";
}
inData.close();
return 0;
}

Search best match of an array into a matrix using std::vector

I've just completed a program which does as follows:
You have t[10][5] and p[10] arrays.
You read dimT and dimP.
You write dimT values in t[][] and dimP values in p[].
For writing values in t[][], you have to fill lines before. The output must be the column which has highest number of matches for the p[] array.
Example:
INPUT -> 14 (dimT) 2 (dimP) 0 1 2 3 4 0 2 7 9 1 0 11 12 0 (t[][]) 0 0 (p[])
So the final matrix display is:
0 1 2 3 4
0 2 7 9 1
0 11 12 0
OUTPUT -> The best matching column is 0 with 2 matches (overlap counted).
I created this program using arrays but it's really horrible, so I'm looking for a better and cleaner solution from some experts possibly, using vectors instead of simple arrays.
Here is my current code. It would be better if I had split it into a function or two more, but it is shorter this way:
#include <iostream>
#include <vector>
using namespace std;
bool IsMatch(vector<double>& col, vector<double>& p, int n)
{
for (size_t i=0; i<p.size() ;i++)
if (col[i+n]!=p[i])
return false;
return true;
}
int main()
{
int dimT;
int dimP;
cin >> dimT;
cin >> dimP;
int lineN = (dimT+5-1)/5;
vector<vector<double> > t(lineN,vector<double>(5));
vector<vector<double> > tTran(5,vector<double>());
vector<double> p(dimP);
t[lineN-1].resize(dimT%5);
//input matrices
for (int i=0; i<dimT;i++) {
double inputVal;
cin >> inputVal;
tTran[i%5].push_back(inputVal);
t[i/5][i%5]=inputVal;
}
for (int i=0; i<dimP;i++)
cin >> p[i];
//print it out
for (int line=0; line<lineN; line++){
for (size_t j=0; j<t[line].size(); j++)
cout << t[line][j] << " ";
cout << endl;
}
//transpose t
/*vector<vector<double> > tTran(5,vector<double>());
for (int line=0; line<lineN; line++)
for (size_t j=0; j<t[line].size(); j++)
tTran[j].push_back(t[line][j]);
//output tTran
for (int line=0; line<5; line++){
for (size_t j=0; j<tTran[line].size(); j++)
cout << tTran[line][j] << " ";
cout << endl;
}
*/
int maxCol=0;
int maxMatchN=0;
for (int col=0; col<5; col++){
int matchN=0;
for (size_t j=0; j<tTran[col].size()-p.size()+1; j++)
if (IsMatch(tTran[col],p,j) )
matchN++;
if (matchN>maxMatchN){
maxMatchN = matchN;
maxCol = col;
}
}
cout << "The best matching column is " << maxCol
<< " with " << maxMatchN << " matches (overlap counted)." << endl;
}
Here is the simpler (all transposed) version I was suggesting in the comments: The point I'm trying to show is that the non transposed copy has no value. You understood it is easier to transpose during input than later. But you kept the non transposed copy as well, and did the output from the non transposed copy and processing from transposed copy.
Take a look at all the extra nonsense that can be skipped if you don't have a non transposed copy. Then compare the output loop directly from the transposed copy to the original output loop. The change to the output loop was trivial and the benefit significant.
int main()
{
int dimT;
int dimP;
cin >> dimT;
cin >> dimP;
vector<double> t[5+1]; // +1 because empty guard vector makes output loop simpler
vector<double> p(dimP);
//input matrices
for (int i=0; i<dimT;i++) {
double inputVal;
cin >> inputVal;
t[i%5].push_back(inputVal);
}
for (int i=0; i<dimP;i++)
cin >> p[i];
//print it out
for (size_t line=0; line<t[0].size(); line++){
for (size_t j=0; line<t[j].size(); j++)
cout << t[j][line] << " ";
cout << endl;
}
int maxCol=0;
int maxMatchN=0;
for (int col=0; col<5; col++){
int matchN=0;
for (size_t j=0; j<t[col].size()-p.size()+1; j++)
if (IsMatch(t[col],p,j) )
matchN++;
if (matchN>maxMatchN){
maxMatchN = matchN;
maxCol = col;
}
}
cout << "The best matching column is " << maxCol
<< " with " << maxMatchN << " matches (overlap counted)." << endl;
}
That empty "guard" vector is a useful trick to know and in more complicated problems avoids a lot of detail and likely mistakes. In this code it just saved needing j<5 && in one spot.