Position of "-1".
In the given NxM matrix find the LAST position of the minus one(-1).
If it will be no "-1" value in the given matrix just output "-1 -1".
Input
First line N and M (1<=N,M<=100).
Then NxM table is given(all number are integers)
Output
First number have to be the row number,and then column number of last "-1" element.
Here is my solution. But I have wrong answer.
#include <iostream>
#include <climits>
using namespace std;
int main () {
int row, col;
double x = 0, y = 0;
cin >> row >> col;
int matrix[row][col];
for (int i = 0; i < row; i++) {
for (int j = 0; j < col; j++) {
cin >> matrix[i][j];
if (matrix[i][j] < 0) {
x = i + 1;
y = j + 1;
}
}
}
if (x == 0 && y == 0)
x = -1, y = -1;
cout << x << " " <<y;
}
Some potential problems:
if (matrix[i][j] < 0) does not check for -1 only. Any negative value will make that condition true.
Unless explicitly specified, I would assume that they want the coordinates with a 0-base, not a 1-base, which would make x = i + 1; and y = j + 1; wrong.
cout << x << " " <<y; is confusing - but you seem to have assigned the row to x and the column to y so I guess it would work if the condition and assignments above were ok.
int matrix[row][col]; is not standard C++. A standard version would be std::vector<std::vector<int>> matrix(row, std::vector<int>(col));
... but - since you only need to print the last position where a -1 is entered, you don't need to store the whole array.
Just read the numbers one by one and check if the entered number is -1. If it is, store the position.
Example:
#include <iostream>
int main () {
int row, col;
int x = -1, y = -1; // if no -1 is found, these will still be -1
if(!(std::cin >> row >> col) || row < 1 || col < 1) return 1;
int value;
for (int i = 0; i < row; i++) {
for (int j = 0; j < col; j++) {
if(!(std::cin >> value)) return 1;
if(value == -1) { // -1 entered, store the position
y = i;
x = j;
}
}
}
std::cout << y << ' ' << x << '\n';
}
Related
I write minesweeper and the current task is to write a function that would uncover the areas that have no mines neighbouring to them. In the original minesweeper if you click within the area with no mines, it would open up an area until there are mines alongside its borders. For that I wrote the function unravel(). Here is the code:
#include <iostream>
#include <cstdlib>
#include <time.h>
#include <vector>
#include <string>
using namespace std;
#define Str1D vector<string>
#define Str2D vector<Str1D>
#define Int1D vector<int>
#define Int2D vector<Int1D>
void unravel(Str2D &fogofwar, Int2D &display, int x, int y) {
for (int minusrows = -1; minusrows < 2; minusrows++){ // going through the
// neighbouring cells (+ the cell itself)
for (int minuscolumns = -1; minuscolumns < 2; minuscolumns++){
if (x + minusrows > 0 && y + minuscolumns > 0 && x + minusrows < fogofwar.size() && y + minuscolumns < fogofwar[0].size()){ // checking
// if within borders
if (x > 0 && y > 0 && x < fogofwar.size() && y < fogofwar[0].size()) { // checking if the oririginal
// values are within borders
fogofwar[x + minusrows][y + minuscolumns] = to_string(display[x + minusrows][y + minuscolumns]); // revealing the
// neighbouring cells
if (display[x + minusrows][y + minuscolumns] == 0) { // if the cell is 0 on the display,
// open it and the 8 neighbouring to it cells
if (not (minusrows == 0 && minuscolumns == 0)) { // if it's not the same cell, of course,
// otherwise it's an endless cycle
unravel(fogofwar, display, x + minusrows, y + minuscolumns);
}
}
}
}
}
}
}
int main() {
int row, column, prob;
bool running = true;
cout << "Input width and height: ";
cin >> row >> column;
cout << endl << "Input mines probability (%): ";
cin >> prob;
cout << endl;
srand (time(NULL));
Int2D field(row + 1, Int1D(column + 1));
Int2D display(row + 1, Int1D(column + 1));
Str2D fogofwar(row + 1, Str1D(column + 1, "*"));
field[0][0] = 0; // field of mines
display[0][0] = 0; // display of neighbouring mines
fogofwar[0][0] = to_string(0); // what the player will see
for (int i = 1; i < row + 1; i++) { //assigning coordinates
field[i][0] = i;
display[i][0] = i;
fogofwar[i][0] = to_string(i);
}
for (int j = 1; j < column + 1; j++) { //assigning coordinates
field[0][j] = j;
display[0][j] = j;
fogofwar[0][j] = to_string(j);
}
for (int i = 1; i < row + 1; i++){ // filling the field with mines
for (int j = 1; j < column + 1; j++){
int x = rand() % 100;
if (x < prob) {
field[i][j] = 1;
}
else{
field[i][j] = 0;
}
}
}
cout << endl << endl;
for (int i = 0; i < row + 1; i++){ // printing field
for (int j = 0; j < column + 1; j++){
cout << " " << field[i][j] << " ";
}
cout << endl;
}
cout << endl << endl;
for (int i = 0; i < row + 1; i++){ // assigning the display of amount of neighbouring mines
for (int j = 0; j < column + 1; j++){
int count = 0;
if (i > 0 && j > 0){
for (int minusrows = -1; minusrows < 2; minusrows++){
for (int minuscolumns = -1; minuscolumns < 2; minuscolumns++){
if (i + minusrows > 0 && i + minusrows < row + 1 && j + minuscolumns > 0 && j + minuscolumns < column + 1){
if (field[i + minusrows][j + minuscolumns] == 1){
count++;
}
}
}
}
display[i][j] = count;
}
cout << " " << display[i][j] << " ";
}
cout << endl;
}
cout << endl << endl;
while (running) {
for (int i = 0; i < row + 1; i++){
for (int j = 0; j < column + 1; j++){
cout << " " << fogofwar[i][j] << " ";
}
cout << endl;
}
cout << endl;
int x, y;
cout << endl << "Input the target cell (x, y): ";
cin >> x >> y;
cout << endl;
unravel(fogofwar, display, x, y);
}
return 0;
}
If I delete the recursivity by changing unravel(fogofwar, display, x + minusrows, y + minuscolumns); to continue; within the function unravel(), it works as intended. But I need to open up the entire area where there are 0's on the display. Any way to skirt the error or fix it for good?
First of all, I am unable to reproduce the error with the information in question. Please try to specify the complete usecase along with what values you are getting into error with.
However, there is an obvious problem in the implementation of unravel.
You go over the same cell multiple times, until the memory exceeds total memory of course (I believe this is the point your program crashes)
You should maintain the slots already visited. You can do this in multiple ways. I am providing one of the ways to handle this.
Try the following code:-
#include <iostream>
#include <cstdlib>
#include <time.h>
#include <vector>
#include <string>
using namespace std;
#define Str1D vector<string>
#define Str2D vector<Str1D>
#define Int1D vector<int>
#define Int2D vector<Int1D>
void unravel(Str2D &fogofwar, Int2D &display, int x, int y, vector<vector<bool> > &visited) {
for (int minusrows = -1; minusrows < 2; minusrows++){ // going through the
// neighbouring cells (+ the cell itself)
for (int minuscolumns = -1; minuscolumns < 2; minuscolumns++){
if (x + minusrows > 0 && y + minuscolumns > 0 && x + minusrows < fogofwar.size() && y + minuscolumns < fogofwar[0].size()){ // checking
// if within borders
if (x > 0 && y > 0 && x < fogofwar.size() && y < fogofwar[0].size()) { // checking if the oririginal
// values are within borders
if (x > 0 && y > 0 && x < visited.size() && y < visited[0].size()) {
cout.flush();
}
visited[x][y] = true;
fogofwar[x + minusrows][y + minuscolumns] = to_string(display[x + minusrows][y + minuscolumns]); // revealing the
// neighbouring cells
if (display[x + minusrows][y + minuscolumns] == 0) { // if the cell is 0 on the display,
// open it and the 8 neighbouring to it cells
if (not visited[x + minusrows][y + minuscolumns]) { // if it's not the same cell, of course,
// otherwise it's an endless cycle
unravel(fogofwar, display, x + minusrows, y + minuscolumns, visited);
}
}
}
}
}
}
}
int main() {
int row, column, prob;
bool running = true;
cout << "Input width and height: ";
cin >> row >> column;
cout << endl << "Input mines probability (%): ";
cin >> prob;
cout << endl;
srand (time(NULL));
Int2D field(row + 1, Int1D(column + 1));
Int2D display(row + 1, Int1D(column + 1));
Str2D fogofwar(row + 1, Str1D(column + 1, "*"));
field[0][0] = 0; // field of mines
display[0][0] = 0; // display of neighbouring mines
fogofwar[0][0] = to_string(0); // what the player will see
for (int i = 1; i < row + 1; i++) { //assigning coordinates
field[i][0] = i;
display[i][0] = i;
fogofwar[i][0] = to_string(i);
}
for (int j = 1; j < column + 1; j++) { //assigning coordinates
field[0][j] = j;
display[0][j] = j;
fogofwar[0][j] = to_string(j);
}
for (int i = 1; i < row + 1; i++){ // filling the field with mines
for (int j = 1; j < column + 1; j++){
int x = rand() % 100;
if (x < prob) {
field[i][j] = 1;
}
else{
field[i][j] = 0;
}
}
}
cout << endl << endl;
for (int i = 0; i < row + 1; i++){ // printing field
for (int j = 0; j < column + 1; j++){
cout << " " << field[i][j] << " ";
}
cout << endl;
}
cout << endl << endl;
for (int i = 0; i < row + 1; i++){ // assigning the display of amount of neighbouring mines
for (int j = 0; j < column + 1; j++){
int count = 0;
if (i > 0 && j > 0){
for (int minusrows = -1; minusrows < 2; minusrows++){
for (int minuscolumns = -1; minuscolumns < 2; minuscolumns++){
if (i + minusrows > 0 && i + minusrows < row + 1 && j + minuscolumns > 0 && j + minuscolumns < column + 1){
if (field[i + minusrows][j + minuscolumns] == 1){
count++;
}
}
}
}
display[i][j] = count;
}
cout << " " << display[i][j] << " ";
}
cout << endl;
}
cout << endl << endl;
while (running) {
for (int i = 0; i < row + 1; i++){
for (int j = 0; j < column + 1; j++){
cout << " " << fogofwar[i][j] << " ";
}
cout << endl;
}
cout << endl;
int x, y;
cout << endl << "Input the target cell (x, y): ";
cin >> x >> y;
cout << endl;
vector<vector<bool> > visited(row+1, vector<bool>(column+1, false));
unravel(fogofwar, display, x, y, visited);
}
return 0;
}
The change is that I am maintaining a visited array, and I never go back to the spot I have already gone to before in unravel.
I have a problem with my homework that asks me to have the compiler print out a matrix in which all the diagonals are outputted as zero. I also have to pass it to a function. However, I have no idea how to do this..
Here is my code:
#include <iostream>
using namespace std;
int diagonals();
int main()
{
//problem 1
int matrix[3][3];
for (int i = 1; i <= 3; i++)
{
for (int j = 1; j <= 3 ; j++)
{
cout << "Row " << i << " column " << j<< ": ";
cin >> matrix[i][j];
}
}
for (int i = 1; i <= 3; i++)
{
for (int j = 1; j <= 3; j++)
{
cout << matrix[i][j] << " ";
}
cout << endl;
}
cout << "\nReverse of the matrix:" << endl;
for (int j = 1; j <= 3; j++)
{
for (int i = 1; i <= 3; i++)
{
cout << matrix[i][j] << " ";
}
cout << endl;
}//end of problem 1
//problem 2
cout << "Diagonals changed to 0:\n" << endl;
}
your matrix declaration says int matrix[3][3]; that it has three 1-D array & in each 1-D array you can store three elements. And in C/C++ array index starts from zero.
Problematic statement is for (int i = 1; i <= 3; i++) as you are skipping matrix[0][0] and trying to store into matrix[3][3] which doesn't exist which in turn causes undefined behavior.
So firstly start iterating loop from 0 to number of rows & column respectively.
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 3 ; j++) {
cout << "Row " << i << " column " << j<< ": ";
cin >> matrix[i][j];
}
}
Coming to task you mentioned, print out a matrix in which all the diagonals are outputted as zero. ? write one condition so that if row value & col value are equal then assign it to zero otherwise scan from user. Here is the sample code
int main(void) {
int matrix[3][3] = { 0 }; /* initialize it */
int row = sizeof(matrix)/sizeof(matrix[0]); /* find no of rows */
int col = sizeof(matrix[0])/sizeof(matrix[0][0]);/* find no of columns */
for (int i = 0; i < row; i++) {
for (int j = 0; j < col; j++) {
if( i == j)
matrix[i][j] = 0;/* when i and j are equal means thats diagonal and assign it to zero */
else /* if its not diagonal then scan from user */
std::cin>>matrix[i][j];
}
}
return 0;
}
Secondly, I also have to pass it to a function. for this learn how to pass 2d array to a function. Here is the sample example.
void diagonal(int (*mat)[3],int row, int col) { /* mat is pointer to an array */
std::cout<<"printing matrix "<<std::endl;
for (int i = 0; i < row; i++) {
for (int j = 0; j < col; j++) {
std::cout<<mat[i][j]<<"\t";
}
std::cout<<std::endl;
}
}
And call diagonal() like below from main() function as
diagonal(matrix,row,col); /* pass matrix, no of rows, no of columns */
I need help, I created a short little program a while ago where it would print a simple pyramid with "*" like this:
*
***
*****
but I decided to challenge myself and see if I could create a simple diamond shape like this:
*
***
*****
***
*
Here is my code so far.
I should also add that the value you input, for example 5, determines how big the diamond is.
#include <iostream>
#include <sstream>
using namespace std;
int main() {
int value = 0;
cout << "Please enter in a value: ";
cin >> value;
cout << endl;
for (int i = 0; i < value; i++) {
//print spaces v v v
for (int x = 0; x < (value - i - 1); x++) {
cout << " ";
}
//print * v v v
for (int y = 0; y < (2 * i + 1); y++) {
cout << "*";
}
cout << endl;
}
for (int i = 0; i < value; i++) {
int number = 0;
number+= 2;
//print spaces v v v
for (int x = 0; x < (value - value + i + 1); x++) {
cout << " ";
}
//print * v v v
for (int y = 0; y < (/*ATTENTION: What do I do here? Plz help*/); y++) {
cout << "*";
}
cout << endl;
}
return 0;
}
What I've been trying to do is figure out what to put inside the parenthesis where it says (//ATTENTION). I've been working for at least an hour trying to do random things, and one time it worked when I input 4, but not for 5, and it's just been very hard. This is key to building the diamond, try putting in just value and compile to see what happens. I need it to be symmetrical.
I need to know what to put inside the parenthesis please. I'm sorry this is very long but the help would be appreciated thanks.
I also apologize if my code is messy and hard to read.
int number = 0; and number+= 2;
value - value inside for (int x = 0; x < (value - value + i + 1); x++) {
are not required.
Inside the parenthesis, you can use
2*(value-i-1)-1
However, I would suggest you to first analyze the problem and then try to solve it instead of trying random things. For instance, let's consider the cases of even and odd inputs i.e., 2 and 3.
Even Case (2)
*
***
***
*
The Analysis
Row Index Number of Spaces Number of Stars
0 1 1
1 0 3
2 0 3
3 1 1
For row index < value
Number of Spaces = value - row index - 1
Number of Stars = 2 * row index + 1
For row index >=value
The number of spaces and stars are simply reversed. In the odd cases, the situation is similar too with a small exception.
Odd Case (3)
*
***
*****
***
*
The Analysis
Row Index Number of Spaces Number of Stars
0 2 1
1 1 3
2 0 5
3 1 3
4 2 1
The small exception is that while reversing, we have to ignore the row index = value.
Now, if we put the above analysis in code we get the solution
//Define the Print Function
void PrintDiamond(int rowIndex, int value)
{
//print spaces v v v
for (int x = 0; x < value - rowIndex -1; x++) {
cout << " ";
}
//print * v v v
for (int y = 0; y < 2 * rowIndex + 1; y++) {
cout << "*";
}
cout << endl;
}
And then inside main
//Row index < value
for (int i = 0; i < value; i++) {
PrintDiamond(i,value);
}
//For row index >= value reversing the above case
//value-(value%2)-1 subtracts 1 for even and 2 for odd cases
//ignore the row index = value in odd cases
for (int i = value-(value%2)-1; i >=0; i--) {
PrintDiamond(i,value);
}
#include <iostream>
#include <sstream>
using namespace std;
int main() {
int value = 0;
cout << "Please enter in a value: ";
cin >> value;
cout << endl;
for (int i = 0; i < value; i++) {
//print spaces v v v
for (int x = 0; x < (value - i - 1); x++) {
cout << " ";
}
//print * v v v
for (int y = 0; y < (2 * i + 1); y++) {
cout << "*";
}
cout << endl;
}
for (int i = 0; i < value-1; i++) {
// int number = 0;
// number+= 2;
// //print spaces v v v
for (int x = 0; x < i+1; x++) {
cout << " ";
}
//print * v v v
for (int y = 0; y < (2*(value-1-i)-1); y++) {
cout << "*";
}
cout << endl;
}
return 0;
}
I hope that you will get this .Also in the second for loop you were iterating it one extra time by iterating the loop upto value. But since the pyramid is symmetric so the no of rows in the pyramid will be 2*value-1.So I in the second loop i should vary upto value -1.
This code should resolve the problem:
#include <sstream>
using namespace std;
void printSpaces(int howMany) {
for(int i = 0; i < howMany; i++) cout << " ";
}
void figure(int size) {
bool oddSize = size % 2 == 1;
int center = size / 2;
int spaces = size / 2;
// If figure is of an odd size adjust center
if (oddSize) {
center++;
} else { // Else if figure is of even size adjust spaces
spaces--;
}
for (int i = 1; i <= center; i++) {
printSpaces(spaces);
for(int j = 0; j < 1 + (i - 1) * 2; j++) cout << "*";
cout << endl;
spaces--;
}
spaces = oddSize ? 1 : 0; // If the figure's size is odd number adjust spaces to 1
center -= oddSize ? 1 : 0; // Adjust center if it's an odd size figure
for(int i = center; i >= 1; i--) {
printSpaces(spaces);
for(int j = 0; j < 1 + (i - 1) * 2; j++)
cout << "*";
cout << endl;
spaces++;
}
}
int main() {
int value = 0;
while(value < 3) {
cout << "Please enter in a value (>= 3): ";
cin >> value;
cout << endl;
}
figure(value);
return 0;
}
I'm working on a code that finds all saddle points in a matrix. Both smallest in their row and biggest in their column, and biggest in their row and smallest in their column fall under the definition (of my university) of a saddle point. Being a beginner I managed to get half of it done (finding saddle points which are smallest in their row and biggest in their column) by copying parts of what we've done in class and typing it myself. I have been stuck on it for quite some time and can't figure how to add the saddle points which are biggest in their row and smallest in their column to the program.
This is what I have so far:
#include <iostream>
#include <cstdlib>
using namespace std;
int a[10][10];
int x, y;
int pos_max(int j) //saddle points check
{
int max = 0;
for (int i = 1; i <= x - 1; i++) {
if (a[i][j] > a[max][j]) {
max = i;
}
}
return max;
}
int main() {
cout << "Enter the number of rows: ";
cin >> x;
cout << "Enter the number of columns: ";
cin >> y;
cout << "----------------------------" << endl;
for (int i = 0; i <= x - 1; i++) //input of the matrix
for (int j = 0; j <= y - 1; j++) {
cout << "a[" << i + 1 << ", " << j + 1 << "] = ";
cin >> a[i][j];
}
cout << "----------------------------\n";
for (int i = 0; i <= x - 1; i++) //visualization of the matrix
{
for (int j = 0; j <= y - 1; j++)
cout << a[i][j] << " ";
cout << endl;
}
cout << "----------------------------\n";
int r;
int flag = 0;
int i = y;
for (int j = 0; j <= y - 1; j++) {
r = pos_max(j);
for (i = 0; i <= y - 1; i++) {
if (a[r][i] < a[r][j]) {
break;
}
}
if (i == y) {
cout << "Saddle points are: ";
cout << "a[" << r + 1 << ", " << j + 1 << "] = " << a[r][j] << "\n";
flag = 1;
}
}
if (flag == 0) {
cout << "No saddle points\n";
}
cout << "----------------------------\n";
return 0;
}
First, there is a logical error with your code. In the pos_max function, it will return the index of the element which is maximum in the column. There can be a case when there are multiple maximum with the same value in the column, however, it returns the one which is not the minimum in the row, hence your program won't be able to print that saddle point.
To solve this, you can either return an array of all indices which are maximum in a column and then check for each of those points if it's minimum in their respective column, but I think it's not a very elegant solution. In any case, you will again have to write the entire code for the other condition for saddle points, minimum in column and maximum in row.
Hence, I would suggest a change in strategy. You create 4 arrays, max_row, max_col, min_row, min_col, where each array stores the minimum / maximum in that row / column respectively. Then you can traverse the array and check if that point satisfies saddle point condition.
Here is the code:
#include <iostream>
#include <cstdlib>
using namespace std;
int a[10][10];
int max_row[10], max_col[10], min_row[10], min_col[10];
int x, y;
bool is_saddle(int i, int j) {
int x = a[i][j];
return (max_row[i] == x && min_col[j] == x) || (min_row[i] == x && max_col[j] == x);
}
int main() {
/* code to input x, y and the matrix
...
*/
/* code to visualize the matrix
...
*/
/* populating max and min arrays */
for (int i = 0; i <= x-1; ++i) {
max_row[i] = a[i][0], min_row[i] = a[i][0];
for (int j = 0; j <= y-1; ++j) {
max_row[i] = max(max_row[i], a[i][j]);
min_row[i] = min(min_row[i], a[i][j]);
}
}
for (int j = 0; j <= y-1; ++j) {
max_col[j] = a[0][j], min_col[j] = a[0][j];
for (int i = 0; i <= x-1; ++i) {
max_col[j] = max(max_col[j], a[i][j]);
min_col[j] = min(min_col[j], a[i][j]);
}
}
/* Check for saddle point */
for (int i = 0; i <= x-1; ++i) {
for (int j = 0; j <= y-1; ++j) {
if (is_saddle(i, j)) {
cout << "Saddle points are: ";
cout << "a[" << i + 1 << ", " << j + 1 << "] = " << a[i][j] << "\n";
flag = 1;
}
}
}
if (flag == 0) {
cout << "No saddle points\n";
}
cout << "----------------------------\n";
return 0;
}
#include <iostream>
using namespace std;
int getMaxInRow(int[][5], int, int, int);
int getMinInColumn(int[][5], int, int, int);
void getSaddlePointCordinates(int [][5],int ,int );
void getInputOf2dArray(int a[][5], int, int);
int main()
{
int a[5][5] ;
int rows, columns;
cin >> rows >> columns;
getInputOf2dArray(a, 5, 5);
getSaddlePointCordinates(a,rows,columns);
}
void getInputOf2dArray(int a[][5], int rows, int columns)
{
for (int i = 0; i < rows; i = i + 1)
{
for (int j = 0; j < columns; j = j + 1)
{
cin >> a[i][j];
}
}
}
void getSaddlePointCordinates(int a[][5],int rows,int columns)
{
int flag = 0;
for (int rowNo = 0; rowNo < 5; rowNo++)
{
for (int columnNo = 0; columnNo < 5; columnNo++)
{
if (getMaxInRow(a, rows, columns, rowNo) == getMinInColumn(a, rows, columns, columnNo))
{
flag = 1;
cout << rowNo << columnNo;
}
}
}
if (flag == 0)
cout << "no saddle point";
cout << "\n";
}
int getMaxInRow(int a[][5], int row, int column, int rowNo)
{
int max = a[rowNo][0];
for (int i = 1; i < column; i = i + 1)
{
if (a[rowNo][i] > max)
max = a[rowNo][i];
}
return max;
}
int getMinInColumn(int a[][5], int row, int column, int columnNo)
{
int min = a[0][columnNo];
for (int i = 1; i < row; i = i + 1)
{
if (a[i][columnNo] < min)
min = a[i][columnNo];
}
return min;
}
just take the reference arr(ref[size]) // memorization method to check the minimum and maximum value in it.
Here is the Code Implementation with time complexity O(n *n) & space complexity O(n):
#include <bits/stdc++.h>
using namespace std;
#define size 5
void util(int arr[size][size], int *count)
{
int ref[size]; // array to hold all the max values of row's.
for(int r = 0; r < size; r++)
{
int max_row_val = arr[r][0];
for(int c = 1; c < size; c++)
{
if(max_row_val < arr[r][c])
max_row_val = arr[r][c];
}
ref[r] = max_row_val;
}
for(int c = 0; c < size; c++)
{
int min_col_val = arr[0][c];
for(int r = 1; r < size; r++) // min_val of the column
{
if(min_col_val > arr[r][c])
min_col_val = arr[r][c];
}
for(int r = 0; r < size; r++) // now search if the min_val of col and the ref[r] is same and the position is same, if both matches then print.
{
if(min_col_val == ref[r] && min_col_val == arr[r][c])
{
*count += 1;
if((*count) == 1)
cout << "The cordinate's are: \n";
cout << "(" << r << "," << c << ")" << endl;
}
}
}
}
// Driver function
int main()
{
int arr[size][size];
for(int i = 0; i < size; i++)
{
for(int j = 0; j < size; j++)
cin >> arr[i][j];
}
int count = 0;
util(arr, &count);
if(!count)
cout << "No saddle points" << endl;
}
// Test case -> Saddle Point
/*
Input1:
1 2 3 4 5
6 7 8 9 10
1 2 3 4 5
6 7 8 9 10
0 2 3 4 5
Output1:
The cordinate's are:
(0,4)
(2,4)
(4,4)
Input2:
1 2 3 4 5
6 7 8 9 1
10 11 12 13 14 15
16 17 18 19 20
21 22 23 24 25
Output2:
No saddle points
*/
Problem statement:
Input is a rectangular bitmap like this:
0001
0011
0110
The task is to find for each black (0) "pixel", the distance to the
closest white (1) "pixel". So, the output to the above should be:
3 2 1 0
2 1 0 0
1 0 0 1
I have a working solution to the problem, which I posted here, asking for advice on performance improvement. In effort to implement #Jerry Coffin's solution (suggested in an answer to the question) I wrote the following code, which, unfortunately, produces garbage output. For example, the output for the input from the problem statement is
1 1 1 0
11 11 0 0
110 0 0 1
Why doesn't the code work?
#include <iostream>
#include <string>
#include <queue>
using namespace std;
const unsigned short MAX = 200;
typedef unsigned short coordinate;
typedef pair<coordinate,coordinate> coordinates;
//Converts char[] to unsigned int
coordinate atou(char* s) {
coordinate x = 0;
while(*s) x = x*10 + *(s++) - '0';
return x;
}
//Returns array of immediate neighbours of pixel of coordinates c
coordinates* neighbours_of(coordinates c) {
static coordinates neighbours[7];
coordinate i = c.first;
coordinate j = c.second;
neighbours[0] = coordinates(i+1,j);
neighbours[1] = coordinates(i+1,j+1);
neighbours[2] = coordinates(i,j+1);
neighbours[3] = coordinates(i-1,j+1);
neighbours[4] = coordinates(i-1,j);
neighbours[5] = coordinates(i-1,j-1);
neighbours[6] = coordinates(i,j-1);
neighbours[7] = coordinates(i+1,j-1);
return neighbours;
}
int main() {
unsigned short test_cases, wave_number, initial_wave_size;
coordinate m, n, i, j;
int A[MAX][MAX];
coordinates* directions;
string row;
queue<coordinates> ones;
queue<coordinates> wave;
coordinates current_coordinates;
bool found_some_zero;
cin >> test_cases;
while(test_cases--) {
//Input
cin >> n;
cin >> m;
for(i = 0; i < n; i++) {
cin >> row;
for(j = 0; j < m; j++) {
if(row[j] == '1') {
A[i][j] = -1;
ones.push(coordinates(i,j));
} else A[i][j] = atou(&row[j]);
}
}
//Initilization
wave = ones;
wave_number = 1;
found_some_zero = true;
//Filling algorithm
while(found_some_zero) {
found_some_zero = false;
initial_wave_size = wave.size();
while(initial_wave_size--) {
current_coordinates = wave.front();
directions = neighbours_of(current_coordinates);
//Try all directions
for(int k = 0; k < 8; k++) {
i = directions[k].first;
j = directions[k].second;
//If on screen and not yet visited
if(i < n && j < m && A[i][j] == 0) {
//Mark visited
A[i][j] = wave_number;
//(i,j) will be part the next wave
wave.push(coordinates(i,j));
found_some_zero = true;
}
}
wave.pop();
}
wave_number++;
}
//-1 to 0
while(!ones.empty()) {
current_coordinates = ones.front();
i = current_coordinates.first;
j = current_coordinates.second;
A[i][j] = 0;
ones.pop();
}
//Output
for(i = 0; i < n; i++) {
for(j = 0; j < m; j++)
cout << A[i][j] << " ";
cout << endl;
}
}
return 0;
}
The input loop is buggy. Instead of
if(row[j] == '1') {
A[i][j] = -1;
ones.push(coordinates(i,j));
} else A[i][j] = atou(&row[j]);
you need to do
if(row[j] == '1') {
A[i][j] = -1;
ones.push(coordinates(i,j));
} else A[i][j] = 0;
Also, neighbors[7] should be neighbors[8], and you should use only the four cardinal directions if you want to match the specified output exactly.