Bowling score calculator in C - c

This is a homework problem. I'm currently in the process of writing a program that calculates one's bowling score. My logic is to use multidimensional arrays with 9 frames as the rows and 2 throws as the columns. I will account for the 10th frame at the very end due to its unique nature of having possibly up to three rolls. The addition of strikes and spares also complicate the question, so I felt like I needed to use arrays to keep track of past and future rolls. I know it's not required but I couldn't think of another way.
Here is my code so far:
for (i=0; i<9; i++)
{
for (j=0; j<2; j++)
{
scanf("%d", &score[i][j]);
tempTotal += score[i][j];
}
}
printf("temporary: %d\n", tempTotal);
//strike
for (i=0; i<9; i++)
{
for (j=0; j<2; j++)
{
if(score[i][0] == 10 && score[i][1] == 0)
{
total = tempTotal + score[i+1][0] + score[i+1][1];
}
//spare
else if ((score[i][0] + score[i][1]) == 10)
{
total = tempTotal + score[i+1][0];
}
else
{
total = tempTotal;
}
}
}
printf("result: %d\n", total);
Here is an update of my progress. As per the comments, I used scanf to fill up my multidimensional array first. And then I looked through the array to account for the cases of strikes and spares. The code works until there are consecutive strikes and/or spares. How do I account for the accumulation of consecutive spares and/or strikes? Am I supposed to add additional conditional statements within my strike and spare conditions to account for if score[i+1][0] is another strike in which case I have to account for that additional 10 points plus the next three throws as well? How can I make such a conditional statement that comprehensively searches through the entire array like that? Any ideas would be appreciated. Thank you.

Related

How many paths does a nested if statement have?

I have a question regarding this metric.
For example, if I have the following code, how many path does the function main have?
void main()
{
int i = 0, j = 0, k = 0;
for (i=0; i<10; i++)
{
for (j=0; j<10; j++)
{
for (k=0; k<10; k++)
{
if (i < 2 )
printf("value is more than 2\n");
if (i > 5)
printf("value is less than 5\n");
}
}
}
}
The first three for loops should have 3 paths and one additional that bypasses all control flow statements, then what about the nested if statement? Is it 1x1 = 1 path?
Anyone without matlab account, the following description is on the website:
A control flow statement introduces branches and adds to the original one path.
if-else if-else: Each if keyword introduces a new branch. The contribution from an if-else if-else block is the number of branches plus one (the original path). If a catch-all else is present, all paths go through the block; otherwise, one path bypasses the block.
For instance, a function with an if(..) {} else if(..) {} else {} statement has three paths. A function with one if() {} only has two paths, one that goes through the if block and one that bypasses the block.
for and while: Each loop statement introduces a new branch. The contribution from a loop is two - a path that goes through the loop and a path that bypasses the loop.
If more than one control flow statement are present in a sequence without any nesting, the number of paths is the product of the contributions from each control flow statement.
For instance, if a function has three for loops and two if-else blocks, one after another, the number of paths is 2 × 2 × 2 × 2 × 2 = 32.
void func()
{
int i = 0, j = 0, k = 0;
for (i=0; i<10; i++)
{
for (j=0; j<10; j++)
{
for (k=0; k<10; k++)
{
if (i < 2 )
;
else
{
if (i > 5)
;
else
;
}
}
}
}
}
In this example, func has six paths: three from the for statements, two from the if statements plus the original path that bypasses all control flow statements.
According to the description:
If more than one control flow statement are present in a sequence without any nesting, the number of paths is the product of the contributions from each control flow statement.
and
The contribution from an if-else block is the number of branches plus one (the original path)
your two if statements contribute 2 paths each, so that's 2 x 2 = 4 paths, and then each of your loop contributes one additional path, so the total would be 7 paths.
However, this description does not make much sense to me, since this code has only one possible path:
if (true) {
// this part is always executed
}
This can seem obvious, but more complicated situations can easily reduce the number of possible paths, just like in your example where there are only three possibilities: either i < 2 or i > 5 or i >= 2 && i <= 5.
I suppose the metric's description would make sense as an upper bound on the number of paths.

Mastermind game in C(with words)

I am probably not going to get help here because my question is far from being specific (I don't even know what exactly wrong with it) but, according to my professor's tests, there is something wrong with it (wrong in terms of correctness - it doesn't provide correct number of direct and indirect matches) (I have no access to his tests). As far as I have been testing, it passes all of my tests. However, there are over a couple hundred million possible outcomes (I think) and I can't test them all because I don't know how to do automated testing...
Here is my code that performs the "logic" part of the game called mastermind, which is compares a string of randomly generated letter (8 max) with user input string (a guess). I wanted to see if anyone has encountered this game in the past and knows the logic of how it supposed to compare two strings and generate the correct number of exact and inexact guesses.
// userInput->position - a length of a string(max 8)
// userInput->code - randomly generated code
// userInput->arr - user input string
void checkForExactMatch(Data* userInput) {
int i;
for (i = 0; i < userInput->position; i++) {
if (userInput->code[i] == userInput->arr[i]) {
userInput->exactMatch++;
userInput->arr[i] = 'a';
}
else
checkForInExactMatch(userInput, i);
}
}
void checkForInExactMatch(Data* userInput, int i) {
int j;
for (j = 0; j < userInput->position; j++) {
if (userInput->arr[j] == userInput->code[i]) {
userInput->arr[j] = 'a';
userInput->inExactMatch++;
break;
}
}
}
Looking over your code there were a couple of observations to be made. First in your for checkForExactMatch() the call to checkForInExactMatch is inside your for loop. So on the first mismatch you call checkForInExactMatch and when you return from checkForInExactMatch -- you call it again on the next iteration unless your first mismatch just happens to be on the final character.
To address that issue, you should fully determine whether you have an exact match or not, completing the for loop before checkForInExactMatch is called.
In your checkForInExactMatch, you have to decide whether a single common-character or some minimum length substring constitutes an inexact match.
It sounds like you have things worked out, and good job for pushing through to a solution. Depending on how you approached it, keeping a simple flag in checkForExactMatch()such as int matched = 1; and then loop turning your test around
for (i = 0; i < userInput->position; i++)
if (userInput->code[i] != userInput->arr[i]) {
matched = 0;
break;
}
Then it's just a simple test of
if (matched) {
userInput->exactMatch++;
userInput->arr[i] = 'a';
}
else
checkForInExactMatch(userInput, i);
So long as what you have done accomplishes something similar, you are fine. Let me know if you have further questions.

Specific for-loop for a simple sort algorithm

this is a simple code for sorting a table from max to min. I am confused because my professor used for(i=0; i<10-1; i++) and I saw that it works fine with for(i=0; i<10; i++). Can please someone tell me the difference?
Thanks for your time, appreciate your help.
int a[10];
int i, j, t;
for(i=0; i<10; i++)
{
scanf("%d", &a[i]);
}
for(i=0; i<10-1; i++)
{
for(j=i+1; j<10; j++)
{
if (a[i]>a[j])
{
t=a[i];
a[i]=a[j];
a[j]=t;
}
}
}
for(i=0; i<10; i++)
{
printf("%d\n", a[i]);
}
Your professor is correct, although your way does work too; it's just clumsier:
Given that the starting value of j is i + 1, in order to avoid a out of bounds access to the array a (the behaviour of which is undefined), you need to constrain i to be less than 9 and i + 1 to be less than 10. Essentially your professor constrains the former, but you constrain the latter.
The bubble sort works this way as sortedness is established once the outer loop has processed the penultimate element.
Converting my comment:
Usually, these kind of algorithms do not stop at the last one, but an element before. In fact, at that point, the nth-1 element is already sorted with respect of the nth one. So, both works, but the "-1" is more efficient because you skip a useless iteration.
In case of for(i=0; i<10; i++) you get one additional iteration of the external loop, in wich i is equal 9. But then in the internal loop j is equal 10 at once, condition j < 10 isn't met, and the internal loop terminates without executing its body.

Gauss Jordan Method in Basic C Multi

I am have a multi-dimensional array that needs to be resolved, to solve for the unknown values (x1,x2,x3,..). In this multi-dimensional array, my array size in the i and j coordinate are different; B[n][n+1]. I know this Basic C, Gauss Jordan Method to solve for the unknown, is incorrect and would like someone to point in how to modify it..
This code is accurate for an Array with the same n values only; eg. A[n][n].
//Computation to solve
for(j=0; j<=n; j++)
{
for(i=0; i<=n; i++)
{
if(i!=j)
{
c=B[i][j]/B[j][j];
for(k=0;k<=n+1;k++)
{
B[i][k] = B[i][k] - c*B[j][k];
}
}
}
}
//Print Solution
printf("\nThe solution is:\n");
for(i=0; i<=n; i++)
{
x[i]=B[i][n+1]/B[i][i];
printf("\n x%d=%.3f\n",i,x[i]);
}
An example would be if my n=2. The array that i would want to solve is B[2][3].
0 -20 0 -1
0 30 -10 0
0 -10 10 1
The output of this code is
x1= -inf
x2=0.050
x3=0.000
The correct output should be
x1=0.00
x2=0.05
x3=0.15
This code is accurate for an Array with the same n values only; eg.
A[n][n].
No, the code already accounts for column n+1 (which holds the right-hand constant terms) in the loop
for(k=0;k<=n+1;k++)
{
B[i][k] = B[i][k] - c*B[j][k];
}
(since k runs up to n+1). So, it is correct in this regard.
An example would be if my n=2. The array that i would want to solve is
B[2][3].
C arrays are declared by specifying the number of elements in the array, not the highest index, so you want B[3][4].
The main fault of the shown code is its lack of the row swapping operation, which may be necessary if B[j][j] is zero, and the related test. We can implement that by inserting
if (!B[j][j])
{
for (i=j+1; i<=n; i++)
if (B[i][j]) { swap(B[j], B[i]); break; }
if (!B[j][j]) continue; // leave all-zero column as is
}
at the beginning of the for(j=0; j<=n; j++) loop body (implementing swap() left to the reader).
The correct output should be
x1=0.00
Whether this is correct is debatable, but if you want a variable where every number is a solution to take the value zero, you may insert
if (B[i][i] == 0 && B[i][n+1] == 0) x[i] = 0;
before the printf("\n x%d=%.3f\n",i,x[i]).

Can't find most frequent word

Hey this is my first post here. i have been assigned with an excercise to count the most frequent word in c programming language. first and foremost i need to read a number which tells me how many words i will have to read. then i need to use calloc with max element size 50. after that i read the strings. my original idea was to create a one-dimensional array which im gonna later sort alphabetically and then counting and printing the most frequent word would be easy. but after some hours of research i found out i need to use a two-dimensional array and things went out of control. ive been studying computer science for 3 months now and this exercise seems tough. do u have any other suggestions?. the example was this:
10
hello
world
goodbye
world
thanks
for
all
hello
the
fish
hello
my code so far is
int main()
{
int i, n, j, temp;
int *a;
printf("Eisagete to plhthos twn leksewn:");
scanf("%d",&n);
a = (int*)calloc(n,50);
printf("Eisagete tis %d lekseis:\n",n);
for( i=0 ; i < n ; i++ )
{
scanf("%d",&a[i]);
}
for (i = 0 ; i < ( n - 1 ); i++)
{
for (j = 0 ; j < n - i - 1; j++)
{
if (a[j] > a[j+1])
{
temp = a[j];
a[j] = a[j+1];
a[j+1] = temp;
}
}
}
dont mind the printfs they are in greek and they are just there to make it look better. i also want to point out that this version is used for integers and not for strings just to start off.
im currently trying a linear search but im not sure if it will help
As you point out, the code you show is related to reading and sorting integers; it is only loosely related to the word counting problem.
How would you count the occurrences of each number? You'd have to
Read the next number;
If you already have a tally for the number, you add one to the tally for that number;
If you've not seen the number before, you create a tally for it and set its count to one.
When all the numbers are read, you search through the set of tallies, looking for the one with the largest count.
Record the number and count of the first entry.
For each subsequent entry:
If the count is larger than the current maximum, record the new maximum count and the entry.
Print the information about the number with the largest count and what that count is.
Replace numbers with words and the general outline will be very similar. You might allocate storage for each string (distinct word) separately.
It is easy to count the number of distinct words or the total number of words as you go. Note that you do not need to store all the words; you only need to store the distinct words. And the count at the front of the list is computer science education gone astray; you don't need the count to make it work (but you probably have to live with it being in the data; the simplest thing is to ignore the first line of input since it really doesn't help very much at all). The next simplest thing is to note that unless they're fibbing to you, the maximum number of distinct words will be the number specified, so you can pre-allocate all the space you need in one fell swoop.
Very simple. Store your words in a 2D array the loop through it and each time you take a word loop through it again starting from the current index and check if there is an equal. ech time the child loop ends check if the number of occurrences is bigger than the last maximum.
#include <stdio.h>
int main()
{
int i, j, occurrence=0, maximum = 0;
char *index_max = NULL;
char wl[10][10] = {"hello","world","goodbye","world","thanks","for","all","hello","the","world"};
for (i=0; i<10; i++){
occurrence = 0;
for (j=i; j<10; j++){
if (!strcmp(*(wl+i), *(wl+j))){
occurrence++;
}
}
if (occurrence>maximum){
maximum = occurrence;
index_max = *(wl+i);
}
}
if (index_max != NULL){
printf("The most frequent word is \"%s\" with %d occurrences.\n", index_max, maximum);
}
return 0;
}

Resources