How to get the third column of text file in C programming - c

I have a text file that contains:
1 1 1
1 2 2
1 3 2
1 7 5
1 8 4
1 9 4
1 10 2
...
and this is my function:
void addRatings()
{
int n,m,l;
int a[50][100];
MovieR = fopen("d://ratings.txt","r");
l = LineNum(MovieR);
MovieR = fopen("d://ratings.txt","r");
for(int i=0;i<l;i++)
{
fscanf(MovieR,"%[^\t]\t%[^\t]\t%[^\t]\n",&n,&m,&a[n][m]);
}
}
Now I want to get the first and second column for n and m
then I want to give third column to the a[n][m].
How can I do that?

You need to read the third value into a temporary variable, and then store that value into the array if and only if the following conditions are met:
fscanf returned 3, meaning that it actually found three numbers
the value for n is between 0 and 49 inclusive
the value for m is between 0 and 99 inclusive
And the code doesn't need to count the number of lines (using LineNum()). The loop should end when fscanf runs out of numbers to read, i.e. returns something other than 3.
The resulting code looks something like this:
void addRatings(void)
{
int a[50][100] = {{0}}; // initialize all ratings to 0
FILE *MovieR = fopen("d://ratings.txt", "r");
if (MovieR != NULL)
{
int n, m, rating;
while (fscanf(MovieR, "%d%d%d", &n, &m, &rating) == 3) // loop until end-of-file
{
if (n < 0 || n > 49 || m < 0 || m > 99) // check for valid indexes
break;
a[n][m] = rating;
}
fclose(MovieR);
}
}

Related

How to read a file, convert letters, and print string and integers to an array in c?

struct reviewStruct {
char reviewer[50];
int feedback[3];
};
int readReviews(FILE *file, struct reviewStruct reviews[10]) {
int i;
file = fopen("Names.txt", "r");
if(file == NULL) {
printf("Error");
exit(-1);
}
for(i = 0; i < 10; i++) {
fgets(reviews[i].reviewer, 50, file);
}
fclose(file);
for(i = 0; i < 10; i++) {
printf("%s", reviews[i].reviewer);
}
return 0;
}
Hello, I'm trying to read a file line by line and print it to an array, with a catch. Whenever a 'Y' or 'y' appears, it converts that letter into a 1, and if an 'N' or 'n' appears, it is converted into a 0 (zero), excluding the first word of every line. For example, I have a file with the following information:
charlie Y n N
priya N n Y
lance y y Y
stan N y n
arin N n N
This is the text file called Names.txt, I want to save the integer information to the array called "feedback", so that it looks like this when printed using a for loop:
1 0 0
0 0 1
1 1 1
0 1 0
0 0 0
How do I populate the feedback array such that it can be printed along with the names using a for loop as it is in the following image?
charlie 1 0 0
priya 0 0 1
lance 1 1 1
stan 0 1 0
arin 0 0 0
Thanks.

logical multiplication of matrices A and B by the operation "AND" and "OR" in C

This is the question:
A logical matrix is a matrix in which all its elements are either 0 or
1.
We define logical multiplication of matrices A and B by the operation
defined below, where "·" is the logical AND operation, and "+" is the
logical OR operation.
In this assignment, you will create two 5x5 logical matrices and find
the corresponding matrix which will be created from "multiply" these 2
matrices
Define global SIZE equals to 5 (Already defined in the template)
Write a function that gets a matrix reference and reads the input
to the matrix from the user. If the input is non-zero replace it by 1.
If the user did not enter enough values before the end of the line,
the remaining cells in the matrix will be populated with zeros. Also
make sure if the user inputs too many characters, you only take what's
needed and discard the remaining input. (Eg: 1509 is a 2x2 matrix with
values 1101, and ‘1 5 ‘ is also a 2x2 matrix with values 1111, the
highlighted whitespace is taken as a 1 as discussed above.)
Function signature: void read_mat(int mat[][SIZE])
Write a function that multiplies, as defined above, two matrices
and enters the results into a third matrix with suitable dimensions.
Function signature: void mult_mat(int mat1[][SIZE],int mat2[][SIZE], int result_mat[][SIZE])
Write a function that prints a matrix into the screen. Please use
“%3d” for printing format to make it look nice as shown below.
Function signature: void print_mat(int mat[][SIZE])
Write the main program which uses the functions above. The program
reads the matrices values from the user, multiplies them and prints
the result matrix on the screen.
The function definitions given are intentional with the return
statements as void. Do not change them. Arrays are transferred between
functions as references rather as primitives like variables. So the
function definitions are perfectly valid. Also, there is no limit on
the input from the user. You can read only the required digits, and
then stop reading, and discard the remaining input.
Here is my code:
#include <stdio.h>
#define SIZE 5
void read_mat(int mat[][SIZE],int size)
{
int i = 0, j = 0, k = 0;
char c;
c=getchar();
while(c!='\n' && k<size*size){
if(c!='0'){
mat[i][j]=1;
j++;
}
else{
mat[i][j]=0;
j++;
}
if (j >= size){
j = 0;
i++;
}
if (i >= size){
return;
}
c=getchar();
k++;
}
}
void mult_mat(int mat1[][SIZE], int mat2[][SIZE], int result_mat[][SIZE])
{
int i,j,k;
for (i = 0; i <SIZE; ++i){
for (j = 0; j <SIZE; ++j)
{
result_mat[i][j] = 0;
for (k = 0; k < SIZE; ++k)
result_mat[i][j] += mat1[i][k] * mat2[k][j];
if(result_mat[i][j]!=0){
result_mat[i][j]=1;
}
}
}
}
void print_mat(int mat[][SIZE],int size)
{
int i, j;
for (i = 0; i < SIZE; i++) {
for (j = 0; j < SIZE; j++)
printf("%3d", mat[i][j]);
printf("\n");
}
//Please use the "%3d" format to print for uniformity.
}
int main()
{
int mat1[][SIZE]={ 0 }, mat2[][SIZE]={ 0 }, res_mat[][SIZE]={0};
printf("Please Enter Values For Matrix 1\n");
read_mat(mat1,SIZE);
printf("Please Enter Values For Matrix 2\n");
read_mat(mat2,SIZE);
mult_mat(mat1,mat2,res_mat);
printf("The First Matrix Is :- \n");
print_mat(mat1,SIZE);
printf("The Second Matrix Is :- \n");
print_mat(mat2,SIZE);
printf("The Resultant Matrix Is :- \n");
print_mat(res_mat,SIZE);
return 0;
}
The input and output should be like this:
Please Enter Values For Matrix 1
111000654987010
Please Enter Values For Matrix 2
11 53
The First Matrix Is :-
1 1 1 0 0
0 1 1 1 1
1 1 0 1 0
0 0 0 0 0
0 0 0 0 0
The Second Matrix Is :-
1 1 1 1 1
1 0 0 0 0
0 0 0 0 0
0 0 0 0 0
0 0 0 0 0
The Resultant Matrix Is :-
1 1 1 1 1
1 0 0 0 0
1 1 1 1 1
0 0 0 0 0
0 0 0 0 0
But when I run the program, this message appears:
exception thrown: Run-Time Check Failure #2 - Stack around the variable 'mat2' was corrupted.
and the output isn't right and I am getting some elements has a junk values:
Please Enter Values For Matrix 1
111000654987010
Please Enter Values For Matrix 2
11 53
The First Matrix Is :-
1 1 1 0 0
0 1 1 1 1
1 1 1 1 1
1 1-858993460-858993460-858993460
-858993460-858993460-858993460-858993460 1
The Second Matrix Is :-
1 1 1 1 1
-858993460-858993460-858993460-858993460-858993460
-858993460-858993460 1 1 1
1 1 1 1 1
1 1 1 1 1
The Resultant Matrix Is :-
1 1 1 1 1
1 1 1 1 1
1 1 1 1 1
1 1 1 1 1
1 1 1 1 1
Another question:
if I entered to the mat1 a big string it's calculated directly without letting me enter a string to mat2 how do I solve this problem ?
int mat1[][SIZE]={ 0 }
will declare a 1x5 matrix. Change it to
int mat1[SIZE][SIZE]={ 0 }

Looking for faults in algorithm for organizing a one-way railway station traffic

I wrote the code below for solving this railway station traffic programming contest question. ( You may read comments and proposed solutions here). However, there are a few exceptional cases for which this code won't work. What are they?
#include <stdio.h>
#include <stdlib.h>
int main(){
int n, i,j;
int * array;
scanf("%i",&n);
array = malloc(sizeof(int) * n);
for(i=0;i<n;++i) scanf("%i",&array[i]);
for(i=0;i<n;++i){
if(i+1 == array[i]) array[i] = -1;
else{
if(array[i] < i+1){
for(j=0;j<i;++j){
if(array[i] == j+1){
if(array[j] == -1){
printf("No\n");
return 0;
}
else array[i] = array[j] = -1;
}
}
}
}
}
for(i=0;i<n;++i) if(array[i] != -1) break;
if(i == n) printf("Yes\n");
else printf("No\n");
return 0;
}
P.S.: I'm assuming this program takes one entry at each time ( rather than waiting for an 0 for signaling the end of input ).
What this code is supposed to do:
1) I'm assuming you've already read what's in this link.
2) After copying a sequence into an array, we must verify whether or not this sequence is valid.
So we use the following algorithm:
Iterate over the sequence, starting from the first element.
If element = element's index + 1 ( because C lists are zero-indexed ), then element = -1.
Otherwise, if and only if element < element's index: We look for a previous element for which ( current element == previous' element index + 1 ) is valid. If this element is found, then now both current element and previous element are changed to -1. If previous element has already been changed before ( that is, it's already -1 ) then this is not a valid sequence.
If after iterating over the list like this any elements are still left, this is not a valid sequence.
Examples:
Example 1
Array: 5 4 3 2 1
5 : 5 > 0 + 1, skip. 4: 4 > 1 + 1, skip. 3: 3 == 2 + 1. Then 3 -> -1.
Array: 5 4 -1 2 1
2 : 2 < 3 + 1. 4 has an index of 1 and 1 + 1 = 2.
Array: 5 -1 -1 -1 1
1: 1 < 4 + 1. 5 has an index of 0 and 0 + 1 = 1.
Array: -1 -1 -1 -1 -1
Therefore this sequence is valid.
Example 2
Array: 5 4 1 2 3
5: 5 > 0 + 1, skip. 4: 4 > 1 + 1, skip. 1: 1 < 2 + 1. 5 has an index
of 0.
Array: -1 4 -1 2 3
2: 2 < 3 + 1. 4 has an index of 1.
Array: -1 -1 -1 -1 3
3: 3 < 4 + 1. -1 ( at position 2 ) has an index of 2. 2 + 1 = 3.
Therefore the sequence is not valid.
Here is an example of an input where your code will give the wrong output:
5
3 4 2 5 1
Your description gave a translation of the code in English, but did not give insight into why that algorithm would solve the problem. So, I just went for a solution where an extra array is used for keeping track of the carriages that are in the station, which will have to function like a stack (First-in-last-out):
#include <stdio.h>
#include <stdlib.h>
int main(){
int n, i;
int carriageAtA = 1;
int * array;
int * station;
int stationSize = 0;
// Read input
scanf("%i",&n);
array = malloc(sizeof(int) * n);
station = malloc(sizeof(int) * n);
for(i=0;i<n;++i) scanf("%i",&array[i]);
// Iterate the desired carriages in sequence
for(i=0;i<n;++i) {
// While the last one in the station is not what we need:
while ((!stationSize || station[stationSize-1] != array[i]) && carriageAtA <= n) {
printf("Move %i from A to station\n", carriageAtA);
// Last carriage in station B is not what we need, so pull one in from A:
station[stationSize] = carriageAtA;
stationSize++; // There is now one more carriage in the station
carriageAtA++; // This is the next carriage at A
}
if (!stationSize || station[stationSize-1] != array[i]) {
// Could not find desired carriage at A nor at station. Give up.
printf("No\n");
return 0;
}
// Drive last carriage at station to B:
printf("Move %i from station to B\n", array[i]);
stationSize--;
}
printf("Yes\n");
return 0;
}
The additional printf calls are just for getting a view of the process. Remove them when you are satisfied.

taking a matrix input from the user in c

I would like to taking a 5x5 matrix input from the user with scanf in c.
for example, if the user type 1 2 3 4 5 6 7 8 9 10, i want to create a 2d array like this: arr[0][0] = 1 , ... arr[1][0]=6 .. etc
the input also can be with new line.
I tried this:
int main() {
int arr[5][5]; eipus(arr);
char c; int r=0; int col=0;
while ((c=getchar()) != EOF) {
if (col >= 5) { col=0; r++; }
if (scanf("%d",&arr[r][col]) == 1) { col++; }
}
printArr(arr);
return 1;
}
eipus() - set the array to 0. printArr - print the array.
the problem is that it always ignores the first number. for example:
[admin#server]$ a.out
1 2 3 4 5 6 7 8
2 3 4 5 6
7 8 0 0 0
0 0 0 0 0
0 0 0 0 0
0 0 0 0 0
number 1 ignored. but if there is a space before 1, it's ok.
getchar() consumes one character. For more interesting result try giving input
12 3 4
You will get the first element to be 2 then.
Use ungetc() to get back the previous state before reading it.
while ((c=getchar()) != EOF) {
ungetc(c,stdin);
if (col >= 5) { col=0; r++; }
if (scanf("%d",&arr[r][col]) == 1) { col++; }
}
By the way you need to make it int c as EOF is nothing but -1
The very first character you enter gets scanned in variable c due to the line
while ((c=getchar()) != EOF) .
You can enter the value scanned c in the matrix elements throughout the loop.

Calculating total number of adjacent integers

I want to calculate the number of integers excluding repeats line by line from the file.
The output I desire is:
Duplicates : 9
Duplicates : 4
Duplicates : 5
Duplicates : 5
Duplicates : 1
Duplicates : 1
Duplicates : 8
For further explanation of the concept:
Take the second line of the file:
1 2 3 4 5 6 5 4 5
At this line there is a 1 so increment the counter because 1 was found first.
Next comes a 2, 2 is not 1 so increment the counter. Next comes a 3, 3 is not a 2 so increment the counter. Next comes a 4, 4 is not a 3 so increment the counter. Next comes a 5, 5 is not a 4 so increment the counter. Next comes a 6, 6 is not a 5 so increment the counter. Next comes a 5, 5 is not a 6 so increment the counter. Next comes a 4, 4 is not a 5 so increment the counter. Next comes a 5, 5 is not a 4 so increment the counter. The number of integers excluding repeats is 9.
Another example:
Take a look a line 8 of the file:
34 34 34 34 34
At this line there is a 34 so increment the counter. Next comes a 34, 34 is 34 so do not increment the counter. Next comes 34, 34 is 34 so do not increment the counter. Next comes a 34, 34 is 34 so do not increment the counter. Next comes a 34, 34 is 34 so do not increment the counter. The number of integers excluding repeats is 1.
EDIT:
I took the suggestion of a user on here and looked at a few link related to adjacent strings and integers. The output is almost completely correct now when compared to the desired output that I listed above. I will only put the pertain code below:
Output:
check1:1
check1:1
check1:2
Duplicates : 6 (Wrong value)
check1:2
Duplicates : 5 (Wrong value)
Duplicates : 5
Duplicates : 5
check1:0
check1:0
check1:0
check1:0
Duplicates : 1
Duplicates : 1
check1:0
check1:0
check1:2
check1:3
check1:3
check1:3
check1:4
check1:5
check1:5
check1:5
check1:5
check1:6
check1:6
Duplicates : 7 (Wrong value)
From the output it appears that whenever a test case goes through the if statement if(array[check] == ch), the output is incorrect.
I have been staring at the loops in this function for a long and I am still stumped.
Any suggestions as to why that loop is leading to incorrect values? Thank you.
Your logic is too complicated, this simple logic should do it
Count the first value
Start a loop from the second value to the last
Subtract the current value from the previous, if the result is 0 then it's the same value, do not add to the counter otherwise add to the counter.
I wrote a program to show you how
numbers.txt
1 2 3 4 5 6 5 4 5
14 62 48 14
1 3 5 7 9
123 456 789 1234 5678
34 34 34 34 34
1
1 2 2 2 2 2 3 3 4 4 4 4 5 5 6 7 7 7 1 1
program.c
#include <stdlib.h>
#include <stdio.h>
int
main(int argc, char **argv)
{
FILE *file;
char line[100];
file = fopen("numbers.txt", "r");
if (file == NULL)
return -1;
while (fgets(line, sizeof(line), file) != NULL)
{
char *start;
int array[100];
int count;
int value;
int step;
count = 0;
start = line;
while (sscanf(start, "%d%n", array + count, &step) == 1)
{
start += step;
count += 1;
}
fprintf(stderr, "%d ", array[0]);
value = 1;
for (int i = 1 ; i < count ; ++i)
{
value += (array[i] - array[i - 1]) ? 1 : 0;
fprintf(stderr, "%d ", array[i]);
}
fprintf(stderr, " -- %d\n", value);
}
fclose(file);
return 0;
}
You simply need to check the current value to previous value of the array and check if they are equal or not something like this ::
int ans = 1;
for (int i = 1 ; i < n ; i++) { //n is the number of elements in array
if (a[i] != a[i - 1]) {
ans++;
}
}
printf("%d", ans);
I do not exactly understand why you use so many check in your code. What I do in this code is that I check my current element in the array (starting from 1) and compare it with previous element, so if they are not equal you have a unique element in your array (sequentially), and hence I increment the ans which is the number of unique elements sequentially.
Here I start with ans = 1 because I assume that there will be at least 1 element in your array and that will be unique in any case.
I don't know what you are using that much code for.
But for what i understand you want to do, it a simple loop like this:
#include <stdio.h>
int main() {
int array[] = {1,3,5,7,9};
int count = 1;
int i = 0;
for(i=1; i<(sizeof(array)/sizeof(array[0])); i++) { //sizeof(array)/sizeof(array[0]) calculates the length of the array
if(array[i]!=array[i-1]) {
count++;
}
}
printf("%d", count);
}

Resources