-2

so i am creating a sudoku validity checker program in C++. the program takes in a csv file with an already completed sudoku board. the program is supposed to read the file line by line and put the numbers into a 2d array (which it's doing just fine). i'm getting stuck on the checking whether or not there are any duplicate numbers in a row (i assume that if i can get this working then the columns should be fairly similar). i know how the algorithm is supposed to work in my head but i just can't seem to get it into code.

Algorithm:

1) look at each row and check for numbers 1 through 9 making sure that they only appear once (if at all)

2) if a duplicate is found (which means that some number is missing) tell the user at what row and column the error was found.

3) otherwise move on to the next row and do it again

i think that it's supposed to be a for loop running this but it's been a long time since i've coded in C++ and nothing on the internet has been very helpful to me.

Any help is appreciated.

Here is my code so far:

#include <iostream>
#include <string>
#include <fstream>
#include <sstream>
#include <thread>

using namespace std;

int *board[9];
int row, col;
void printBoard();
void is_row_ok();

int main()
{
    for (int i = 0; i < 9; ++i)
    {
        board[i] = new int[9];
    }
    printBoard();
    is_row_ok();
    cout << endl;
    return 0;
}

void printBoard()
{
    string line;
    string val;
    ifstream myFile("Testfile1.txt");

    for (int row = 0; row < 9; ++row)
    {
        string line;
        getline(myFile, line);
        if (!myFile.good())
            break;

        stringstream iss(line);
        cout << endl;

        for (int col = 0; col < 9; ++col)
        {
            string val;
            getline(iss, val, ',');
            if (!iss.good())
                break;

            stringstream convertor(val);
            convertor >> board[row][col];
            cout << board[row][col] << "  ";
        }
    }
    cout << endl;
    cout << endl;
}
void is_row_ok()
{
    bool found = false;
    int i, j;
    for (int i = 0; i < 10; ++i) //<------ edit starts here
    {
        int counter = 0;
        for (int j = 0; j < 9; ++j)
        {
            if(board[row][j] == i)
            {
                cout << "Before " << counter << endl;
                counter++;
                cout << counter << endl;
            }
            if(counter > 1)
              break;
        }
    }
}
Marc Karam
  • 445
  • 6
  • 22

2 Answers2

2

The easiest way I can think of is 2 loops (one inside of another): 1 gets you through numbers 1 to 9 and the other goes through the elements of the row. Small tip with code.

for(int i=1;i<10;i++){
   int counter =0;
   for(int j=0;j<9;j++){
      if(board[row][j] ==i)counter ++;
   }
   if(counter >1) break; //here you check that there´s only one number on the row.
}

Of course, there are other ways to do it, this one is quite basic and slow.

-------------------------------------EDIT-------------------------------------------

Your function should be bool in order to know if there´s repeated number or not.

bool is_row_ok(vector<vector<int> board)//I suggest you use vectors instead of arrays.
{
    //i and j are declared on for, there´s no need to declare them again.
    for (int i = 0; i < 10; ++i) 
    {
        int counter = 0;
        for (int j = 0; j < 9; ++j)
        {
            if(board[row][j] == i)counter++;
            if(counter > 1)return false;
        }
    }
return true;
}

Now you call this function on main. If function returns true, everything is ok, if it returns false, you have a repeated number.

int main(){
  if(is_row_ok(board)cout<<"No number repeated"<<endl;
  else cout << "Number repeated"<<endl;
  return 0;
}
Capie
  • 976
  • 1
  • 8
  • 20
  • i've implemented your code above and added some print statements and when i ran it it printed out a bunch of repeating "Before 0" 's and then "1" 's. did i do something wrong? – Marc Karam Mar 06 '17 at 02:50
  • You are printing the counter, which is 0 or 1. If it´s 2 , it leaves the loop, so yes, it´s ok. I see you are using a boolean. I will edit my code to make it work. – Capie Mar 06 '17 at 20:24
0

I think the easiest way is to use std::sort + std::unique as unique returns iterator to the new end of range.

#include <algorithm>
using namespace std;

int main()
{
    int n[15] = { 1, 5, 4, 3, 6, 7, 5, 5, 5, 4, 2, 3, 9, 8, 9 };

    int* end = n + 15;
    sort(n, n + 15);
    bool has_no_duplicates = (unique(n, n + 15) == end);

    return 0;
}

This is just an example but you should get the idea.

mpiatek
  • 1,313
  • 15
  • 16