2d array output values incorrect - c

I have this code and have no idea why my output is incorrect. I'm used to C++ not C.
Run using: ./sudoku.o < inputfile
int row = 8;
int col = 8;
int puzzle[row][col];
for (int r = 0; r < row; r++){
for (int c = 0; c < col; c++){
scanf("%d", &puzzle[r][c]);
}
}
for (int r = 0; r < row; r++){
for (int c = 0; c < col; c++){
printf("%d", puzzle[r][c]);
}
printf("\n");
}
this is my input
827154396
965327148
341689752
593468271
472513689
618972435
786235914
154796823
239841567
and this is the output I'm getting
-132765-84896035232594-208491627232765-208491623232765
00-84896120832594-84897084832594-85115713632594
10-848970848325941000
10-8489612083259400-208491648032765
1700966438000-84896035232594-208491641632765
-20846176001-208491643232765-163754450041951850
-1000-85506816832594-84897220032594
0000-20849160083276500

As noted in the comments, you should check that scanf() is successful (in this context, returns 1), and you need to make sure it reads only single digits with "%1d". Like this:
#include <stdio.h>
int main(void)
{
int row = 8;
int col = 8;
int puzzle[row][col];
for (int r = 0; r < row; r++)
{
for (int c = 0; c < col; c++)
{
if (scanf("%1d", &puzzle[r][c]) != 1)
{
fprintf(stderr, "Failed to read puzzle[%d][%d]\n", r, c);
return 1;
}
}
}
for (int r = 0; r < row; r++)
{
for (int c = 0; c < col; c++)
{
printf("%d", puzzle[r][c]);
}
printf("\n");
}
return 0;
}
With your data file, the output is (surprise, surprise):
82715439
69653271
48341689
75259346
82714725
13689618
97243578
62359141
"Ah", you said, "I wanted 9 numbers per line". But your code doesn't say that; you set row and col to 8, so you only read 8 numbers per row of the matrix, and only 8 rows. And the ninth number on the first row of date becomes the first number on the second row of your matrix, etc.
Change the limits to 9 to get the result you really wanted:
827154396
965327148
341689752
593468271
472513689
618972435
786235914
154796823
239841567
If you want line-by-line input (not necessarily a bad idea), you'd need to use fgets() (or perhaps POSIX
getline()) to read lines, and then
sscanf() to read the numbers — see How to use sscanf() in loops?

Related

How do I properly nest these loops in C?

I need to make a program that prints this:
.......#
......##
.....###
....####
...#####
..######
.#######
########
Basically, if the n is 8. it will print 7 dots and 1 hash***. then in the next row it will print 7 dots and 2 hashes, then 6 dots and 3 hashes until there are 0 dots and 8 hashes.
So far my code looks like this:
int main(void)
{
int G = 1;
int n = 8;
int m = 0;
int k = 0;
int Z = 1;
for (m = n; m > 0; m --)
{
for (k = n - 1; k >= Z; k --)
{
printf(".");
}
printf("\n");
Z = Z + 1;
}
for (int i = 0; i < n; i ++)
{
for (int j = 0; j < G; j++)
{
printf("#");
}
printf("\n");
G = G + 1;
}
}
But the result of this comes out as this:
.......
......
.....
....
...
..
.
#
##
###
####
#####
######
#######
########
Since this is obviously homework or some self studies, I'll write how you need to think here.
The first problem is to be able to print ONE row given total number of rows and current row.
So let's start with total number or rows. I will use more descriptive variable names, which you also should.
int total = 8;
Now we need to print one row, given the current row. Let's assume that the first row has number 1. Let's start with the dots.
for(int i=0; i<(total-row); i++)
printf(".");
Then we continue with the hashes:
for(int i=0; i<row; i++)
printf("#");
And now we just need to do this total times and add a newline after each:
for(int row=1; row<total; row++) {
for(int i=0; i<(total-row); i++)
printf(".");
for(int i=0; i<row; i++)
printf("#");
printf("\n");
}
Please note that it is very common with obo (off by one) errors when doing things like this. We could let 0 be the first row instead of one, but then we need to change a few other things. You said you wanted 1 hash and 7 dots on first line and 8 hash and 0 dots on last line, which seems a bit odd, but just change row<total to row<total+1 and you get that.
You'll rather want something that does the printing from within the same loop. Here's some pseudo code of a simple way to write this algorithm:
for(int dots=n-1; dots>DOTS_MIN; dots--)
{
for(int i=0; i < dots; i++)
print dot
for(int i=dots; i < n; i++)
print hash
printf("\n");
}
First, start from naming, it's a challenging task to find out what Z stands for.
So we have
int totalRows = 4;
int totalColumns = 8;
and we should print out totalRows of rows:
for (int row = 1; row <= totalRows; ++row) {
}
from 2nd row on we should add a new line:
for (int row = 1; row <= totalRows; ++row) {
/* Start a new line from the 2nd row on */
if (row > 1)
printf("\n");
}
Time to print dots, we have totalColumns - row of them:
for (int i = 1; i <= totalColumns - row; ++i)
printf(".");
Followed by row # symbols:
for (int i = 1; i <= row; ++i)
printf("#");
Combining these chunks all together:
int main() {
int totalRows = 4;
int totalColumns = 8;
for (int row = 1; row <= totalRows; ++row) {
/* Start a new line from the 2nd row on */
if (row > 1)
printf("\n");
/* Printing dots */
for (int i = 1; i <= totalColumns - row; ++i)
printf(".");
/* Printing # */
for (int i = 1; i <= row; ++i)
printf("#");
}
return 0;
}

Checking whether a number exist in the same row or column matrix

I want to output Yay if the matrix doesn't contain the same number on the same row or column otherwise output Nay
this is for my college homework. I already tried to check the column and row in the same loop but the output still not right
#include <stdio.h>
int main()
{
int size;
int flag;
scanf("%d",&size);
char matrix[size][size];
for (int i = 0; i < size; i++)
{
for (int l = 0; l < size; l++)
{
scanf("%s",&matrix[i]);
}
}
for (int j = 0; j < size; j++){
for (int k = 0; k < size; k++){
if(matrix[j] == matrix[j+1] || matrix[j][k]==matrix[j][k+1])
{
flag = 1;
}
else
{
flag = 0;
}
}
}
if (flag == 1)
{
printf("Nay\n");
}
else
{
printf("Yay\n");
}
return 0;
}
I expect to output "Nay" when I input
3
1 2 3
1 2 3
2 1 3
and "Yay" when i input
3
1 2 3
2 3 1
3 1 2
Your matrix is a 2D array and you are referencing it using only a single subscript matrix[index] at several places which returns the address of the row. Index it using both the row and column indices. Try the code below:
{
int size;
int flag;
scanf("%d",&size);
char matrix[size][size];
for (int i = 0; i < size; i++)
{
for (int l = 0; l < size; l++)
{
scanf("%s",&matrix[i][l]);
}
}
for(int j = 0; j < size; j++){
for (int k = 0; j < size; j++){
if(matrix[j][0]== matrix[j][k] || matrix[k][0]==matrix[k][j])
{
flag = 1;
break;
}
else
{
flag = 0;
}
}
}
if (flag == 1)
{
printf("Nay\n");
}
else
{
printf("Yay\n");
}
return 0;
}
Your have a logic problem. Your flag is reset on every element in the matrix and thus only reflects the result of the last check.
In addition, you need a break; in your nested loop. The logic is, if your flag becomes 1, you are sure to say Nay, and you don't want the flag to be reset to 0.
int flag = 0;
for (int i = 0; i != size && !flag; ++i) {
for (int j = 0; j != size; ++j) {
if ( /* detection */ ) {
flag = 1;
break;
}
}
}
if (flag)
printf("Nay\n");
else
printf("Yay\n");
Note: The commented /* detection */ part requires more work. Since it's your homework, you may try it first. You could use a hash table for memorization. Or brutal force to make the program simply work. It seems that your detection only checks for neighboring elements, which is not sufficient to assert that an element is unique in its row or column. Consider
1 2 1
3 4 5
6 7 8
I can't do your homework for you. The following is the brutal-force way you may consider.
The if ( /* detection */ ) part could be if (has_same_element(matrix, i, j)), with a function (pseudo code)
int has_same_element(matrix, row, col)
{
for each element a in matrix's row except matrix[row][col] itself
if (a == matrix[row][col])
return 1
for each element b in matrix's col except matrix[row][col] itself
if (b == matrix[row][col])
return 1
return 0
}
Of course there are smarter ways, like using a hash table, in which case you don't even need the nested loop. For the time being, work out a feasible solution, instead of the best solution.

How to normalize a matrix in C?

How to normalize a matrix?
Suppose I have a 2x3 matrix:
1 2 3
4 5 6
The normalized matrix would be:
1/sqrt(pow(2,2) + pow(3,2)) 2/sqrt(pow(2,2) + pow(3,2)) 3/sqrt(pow(2,2) + pow(3,2))
4/sqrt(pow(5,2) + pow(6,2)) 5/sqrt(pow(5,2) + pow(6,2)) 6/sqrt(pow(5,2) + pow(6,2))
This is my sample code:
#include <stdio.h>
#include <conio.h>
#include <math.h>
int main(){
int rows, cols, rowCounter, colCounter, r, c;
int initial[100], inputMatrix[100][100], rowSum[100] = {0}, norm[100][100], square[100] = {0};
printf("Enter size of a matrix\n");
scanf("%d %d", &rows, &cols);
printf("Enter matrix of size %dX%d\n", rows, cols);
/* Input matrix */
for(rowCounter = 0; rowCounter < rows; rowCounter++){
for(colCounter = 0; colCounter < cols; colCounter++){
scanf("%d", &inputMatrix[rowCounter][colCounter]);
}
}
for(r = 0; r < rows; r++)
{
for(c = 1; c < cols; c++)
{
float a;
a == inputMatrix[r][c];
square[r] += pow(a, 2);
}
printf("%.2lf ", square[r]);
}
for(rowCounter = 0; rowCounter < rows; rowCounter++)
{
for(colCounter = 0; colCounter < cols; colCounter++)
{
norm[rowCounter][colCounter] == (inputMatrix[rowCounter][colCounter]) / sqrt(square[rowCounter]);
}
}
printf("\nNormalized Matrix:\n");
for(rowCounter = 0; rowCounter < rows; rowCounter++)
{
for(colCounter = 0; colCounter < cols; colCounter++)
{
printf("%.3lf ", norm[rowCounter][colCounter]);
}
printf("\n");
}
getch();
return 0;
}
Why are you using == here:
for(r = 0; r < rows; r++)
{
for(c = 1; c < cols; c++)
{
float a;
a == inputMatrix[r][c]; //look here
square[r] += pow(a, 2);
}
It should be:
for(r = 0; r < rows; r++)
{
for(c = 1; c < cols; c++)
{
float a;
a = inputMatrix[r][c];
square[r] += pow(a, 2);
}
The same here:
norm[rowCounter][colCounter] == (inputMatrix[rowCounter][colCounter]) / sqrt(square[rowCounter]);
It should be:
norm[rowCounter][colCounter] = (inputMatrix[rowCounter][colCounter]) / sqrt(square[rowCounter]);
And you should be careful here:
int initial[100], inputMatrix[100][100], rowSum[100] = {0}, norm[100][100], square[100] = {0};
Are you sure about use int for all of this declarations?
I think you should use double or float instead, at least in some of them.
There are some problems in your code, I'll try to address the most important ones.
Your norm matrix is a 2D array of int as inputMatrix, but you have to use an array of float or double to correctly store the result and to perform the right calculation. In C if both of the terms of a division are integers types an integer division (like: 3/2 = 1, not 1.5) is performed, which is not what you need.
Another mistake is to use == instead of = to perform an assignment. In C == is the 'equal to' relational operation.
EDIT
As #chux pointed out it would be wiser to choose a more accurate type for a and square[]. Using long long int will (may) prevent numeric overflow in case the elements of the matrix are too big for their square or the sum of them to be reprensented by an int.
Be aware that if you decide to use double instead there are other subtle numerical issues concernig the sum of small number (and the order in which it is performed) represented by floating point types. So, as a partial remedy, you can use long double (if it really has more precision then double in your environment) for a and square.
EDIT 2
In the question and in comment you say that the first element of each row of the matrix is supposed to be "constant in the matrix" so it doesn't take part to the sum of squares in your code and in the example you gave, but in both of them they are updated in the next loop. I'm not sure of what is going on, so I corrected my code to mimic the behavior of yours.
Here is a working corrected version of your code:
#include <stdio.h>
#include <math.h>
int main() {
int rows, cols, r, c;
// you may think about dynamical allocation here
int inputMatrix[100][100], rowSum[100] = {0};
// it's better to use a type that can manage bigger numbers to avoid numeric overflow
long long int a, square[100] = {0};
// your starting matrix can be a matrix of int but the normalized one need to
// contain floating point numbers
double norm[100][100], k;
printf("Enter size of a matrix\n");
scanf("%d %d", &rows, &cols);
printf("Enter matrix of size %dX%d\n", rows, cols);
/* Input matrix */
for ( r = 0; r < rows; r++) {
for (c = 0; c < cols; c++) {
scanf("%d", &inputMatrix[r][c]);
// ^^ if you are scanning integer numbers...
}
}
printf("\nrows: %d cols: %d elements:\n",rows,cols);
for( r = 0; r < rows; r++) {
for( c = 0; c < cols; c++) {
printf("%d ", inputMatrix[r][c]);
// ... ^^ you should print integer numbers
}
printf("\n");
}
for (r = 0; r < rows; r++) {
for (c = 1; c < cols; c++) {
// ^^^ I don't know why you skip this here
a = inputMatrix[r][c];
//^ You have to assign, not to compare!
square[r] += a * a;
// ^^^^^ no need to call pow()
}
printf("Sum of squares of row %d: %lld\n",r,square[r]);
// square contains int ^^
// It would be nice and safer if you check here if square == 0 to avoid a
// division by zero and probably detect bad input data
}
for ( r = 0; r < rows; r++ ) {
// It's far more efficient to precalculate this term, even if compilers
// could be smart enough to do it for you. You may want to store those
// values in an array of doubles instead of the (sum of) squares
k = 1.0 / sqrt(square[r]);
for( c = 0; c < cols; c++ ) {
norm[r][c] = k * inputMatrix[r][c] ;
// again, ^ assign not compare
}
}
// you can add the printf to the previous loop...
printf("\nNormalized Matrix:\n");
for( r = 0; r < rows; r++) {
for( c = 0; c < cols; c++) {
printf("%.3lf ", norm[r][c]);
// ^^^^^ norm contains double
}
printf("\n");
}
return 0;
}
I keep the input matrix of integer type, but it would be better to use double for that too. As i added a print loop for the original matrix, the final output is:
rows: 2 cols: 3 elements:
1 2 3
4 5 6
Sum of squares of row 0: 13
Sum of squares of row 1: 61
Normalized Matrix:
0.277 0.555 0.832
0.512 0.640 0.768

Input to Multi-Array in C

I am trying to assign user input into an array; however, the program below only picks up on the first element in each line of input. The ultimate goal of this program is to find the diagonal sums of integers and return the absolute value of their difference.
Example input (note that the first number gives the number of rows and columns (square array):
Input:
3
11 2 4
4 5 6
10 8 -12
Output:
Expected = 15
Actual = 10
I realize that the issue lies in the way that the array is setup. If I print the array out I get: 111555999
Any hints/help would be very appreciated.
int main() {
int n, i, c, multi_array[200][200], sum1 = 0, sum2 = 0;
scanf("%i", &n); //N = number of rows and number of columns (square 2D array)
for (i = 0; i < n; i++) {
for (c = 0; c < n; c++) {
scanf("%d ", &multi_array[c][i]); //enter integers to store in array
}
}
for (i = 0; i != n; i++) {
sum1 += multi_array[i][i]; //add up top left to bottom right diagonal
}
for (i = 0; i != n; i++) {
sum2 += multi_array[i][n-i]; //add up top right to bottom left diagonal
}
printf("%i", abs(sum1 - sum2)); //print absolute value of the difference between diagonals
return 0;
}
Your major problem is here, where you go out of bounds:
for (i = 0; i != n; i++) {
sum2 += multi_array[i][n - i]; // when i is 0, th
}
When i = 0, you are accessing multi_array[0][3], which is out of bounds when N = 3.
So change it to this:
multi_array[i][n - i - 1]
You should read your array like this:
for (i = 0; i < n; i++) {
for (c = 0; c < n; c++) {
scanf(" %d ", &multi_array[i][c]);
}
}
since C stored its arrays in row-major order. What you have stores the array in column-major order. It's not wrong, but it's something you do only if you really have to.
Finally, change again the input part of your code to this:
scanf("%d", &n);
for (i = 0; i < n; i++) {
for (c = 0; c < n; c++) {
scanf("%d", &multi_array[i][c]);
}
}
so that you have to input exactly what you need to. With your initial code I have to type an extra random number when I had completed the input process.
Last but not least, I am posting the whole code, where I have wrote some extra printf()'s, which are actually for the programmer, so that he can see step-by-step if his code is acting as expected or not.
#include <stdio.h>
#include <stdlib.h> /* abs */
int main() {
int n, i, c, multi_array[200][200], sum1 = 0, sum2 = 0;
scanf("%d", &n);
for (i = 0; i < n; i++) {
for (c = 0; c < n; c++) {
scanf("%d", &multi_array[i][c]);
}
}
for (i = 0; i < n; i++) {
for (c = 0; c < n; c++) {
printf("|%d|", multi_array[i][c]);
}
printf("\n");
}
for (i = 0; i != n; i++) {
sum1 += multi_array[i][i];
}
printf("sum1 is %d\n", sum1);
for (i = 0; i != n; i++) {
sum2 += multi_array[i][n - i - 1];
}
printf("sum2 is %d\n", sum2);
printf("%i", abs(sum1 - sum2));
return 0;
}
Output:
3
11 2 4
4 5 6
10 8 -12
|11||2||4|
|4||5||6|
|10||8||-12|
sum1 is 4
sum2 is 19
15
You are clearly going out of bounds here:
for (i = 0; i != n; i++) {
sum2 += multi_array[i][n-i]; //add up top right to bottom left diagonal
}
When i is equal to 0 the expression n-i will be equal to n, but the range of the array is from 0 to n-1. The code will read uninitialized values and cause undefined behavior.
The second array index should be 1 less.

C, Showing count of repeating symbols

Need to figure out a code that counts all the repeating symbols in a string. As you can see below, so far so good.
And here starts the tricky part, at the end of the code I want to output symbols in an order they were typed which had for example 2 occurences in a string, and I got problems figuring that out.
int counts[256] = { 0 };
int i;
size = strlen(text);
for (i = 0; i < size; i++) {
counts[(int)(text[i])]++;
}
for (i = 0; i < 256; i++) {
printf("The %d. character has %d occurrences.\n", i, counts[i]);
}
Just iterate through the source string again and for each character look into your counts array.
If you don't want to print the same statistics for every occurence of repeating character, you can reset the corresponding counts value to zero just after you print the statistics, and have an additional check before printing.
for(i = 0; i < size; i++) {
if(counts[(int)(text[i])] == 2)
printf("%d", (int)(text[i]));
The first line loops through your source string for the order of occurences.
The second line checks if it was captured in the counts array as occuring only twice.
If it was we print the char code on the third line.
To only print the character once:
for(i = 0; i < size; i++) {
if(counts[(int)(text[i])] == 2) {
printf("%d", (int)(text[i]));
counts[(int)(text[i])] = 0;
}
}
Here is an implementation of Inspired's answer:
int counts[256] = { 0 };
char text[] = "Hello, world!";
int i, size = strlen(text);
for (i = 0; i < size; i++)
{
counts[(unsigned int)(text[i])]++;
}
for (i = 0; i < size; i++)
{
if (counts[(unsigned int)text[i]] > 1)
{
printf("%c", text[i]);
counts[(unsigned int)text[i]] = 0; // Remove to print repeats.
}
}
Make a key,count pair, like:
#include <string.h>
#include <stdio.h>
int main()
{
char* text = "count this text";
char *keys = new char[strlen(text)];
int* count = new int[strlen(text)];
int last = 0; int j=0;
for(int i=0; i<strlen(text); i++){
for(j=0; j<last; j++){
if(keys[j]==text[i]) break;
}
if(keys[j]==text[i]){
count[j]++;
} else {
keys[last]=text[i];
count[last]=1;
last++;
}
}
for(int i=0; i<last; i++){
printf("%c %d\n", keys[i], count[i]);
}
}
so you keep the order in the text and get the count.
On execution the output is:
c 1
o 1
u 1
n 1
t 4
2
h 1
i 1
s 1
e 1
x 1

Resources