Weird Output with first case integer - c

Here are two functions below that compile perfectly but I seem to be getting a weird error with the very first inputted integer. I have tried debugging in GDB but when it's only the first inputted value that is having this weird error, then it makes things complicated.
#include <stdio.h>
#include "Assg9.h"
#include <stdlib.h>
#include <assert.h>
#include <math.h>
void getPrimes(int usernum, int* count, int** array){
(*count) = (usernum - 1);
int sieve[usernum-1], primenums = 0, index, fillnum, multiple;
for(index = 0, fillnum = 2; fillnum <= usernum; index++, fillnum++){
sieve[index] = fillnum;
}
for (; primenums < sqrt(usernum); primenums++)
{
if (sieve[primenums] != 0){
for (multiple = primenums + (sieve[primenums]); multiple < usernum - 1; multiple += sieve[primenums])//If it is not crossed out it starts deleting its multiples.
{
if(sieve[multiple]) {
--(*count);
sieve[multiple] = 0;
}
}
}
}
int k;
for (k = 0; k < usernum; k++)
if (sieve[k] != 0)
{
printf("%d ", sieve[k]);
}
*array = malloc(sizeof(int) * (usernum +1));
assert(array);
(*array) = sieve;
}
void writeToOutputFile(FILE *fpout, const int *array, int n, int count){
int i;
fprintf(fpout, "There are %d prime numbers less than or equal to %d \n", count, n);
for(i = 0; i < count; i++)
{
if(*(array + i) != 0){
fprintf(fpout, "%d ", *(array + i));
}
}
}
Our Output:
Please enter an integer in the range 2 <-> 2000 both inclusive: 2
2 32664
Do you want to try again? Press Y for Yes and N for No: y
Please enter an integer in the range 2 <-> 2000 both inclusive: 2
2
Do you want to try again? Press Y for Yes and N for No: n
Good bye. Have a nice day
Expected output should obviously just display 2. This is the case for any integer from 2-2000 for the very first inputted integer. The very last, or last 2, prime numbers print very large numbers, sometimes even negative numbers. I have no clue why, but after the first inputted value everything works perfectly. Tried debugging this with GDB like crazy but with no luck. Would really appreciate someone's help for this bizarre error

You aren't initializing the sieves array to 0s. So you're looping from 0 to usernum-1, printing out every number that isn't a 0. Since you didn't initialize the array, the 2nd element is a random value and is being printed out

This code is a problem:
(*array) = sieve;
You are are assigning the address of sieve, a temporary local array, to *array. You need to copy the array contents instead.
Are you also this person who has asked three questions about identical code?

Related

Double arrays in C

Im in the process of learning C and the basis of the class is C primer plus(6th edition). We use Eclipse as an IDE.
For an project we have to create to arrays. One array that takes numbers in a loop and another array that display the cumulative value. So if array 1 has values 1, 5 and 3(out of 10 inputs total) then the resulting input in array 2 should be 9(on the 3th input because of the 3 inputs in array 1).
Im having trouble getting started the right way - anyone here has ideas how I could proceed?
So far I have this for starters but forgive me for it it very weak:
#include <stdio.h>
#include <stdlib.h>
#define SIZE 10
void doublearrays (double usernumber);
int main(void)
{
double usernumbers = 0.0;
int loop1 = 1;
while(loop1)
{
printf("Type numbers as doubles. \n");
fflush(stdout);
loop1 = scanf("%lf", &usernumber);
if(loop1)
{
doublearrays(usernumber);
}
}
return 0;
}
All the text in a homework assignment shall be read:
For a project we have to create two arrays... 10 inputs total...
Why on earth do not you declare them?... You already have defined SIZE so
double usernumbers[SIZE];
double cumulnumbers[SIZE];
Next do yourself a favour and handle one problem at a time:
One array that takes numbers in a loop...
Ok, so write a loop up to 10 reading floats directly into the array and note how many numbers were received
int n;
for(n=0; n<SIZE; n++) {
if (scanf("%lf", &usernumbers[n]) != 1) break;
}
// ok we now have n number in the first array
Let us go on
and another array that display the cumulative value.
Ok cumul is initially 0. and is incremented on each value from the first array:
double cumul = 0.;
for(int i=0; i<n; i++) {
cumul += usernumbers[i];
cumulnumbers[i] = cumul;
}
(your current code isn't what you need... delete it and then...)
anyone here has ideas how I could proceed?
Well the first step would be to actually define some arrays.
double input[SIZE];
double cum[SIZE];
The next step would be a loop to read input.
for (int i = 0; i < SIZE; ++i)
{
if (scanf("%lf", &input[i]) != 1)
{
// Input error - add error handling - or just exit
exit(1);
}
}
The next step is to add code for calculating the the cumulative value.
I'll leave that for you as an exercise.
The last step is to print the array which I also will leave to you as an exercise.
The straight forward way of doing this, which would also use two arrays and a loop construct would be to create something like this.. I've changed the doubles to integers. (and i am also ignoring any errors from scanf()).
#include <stdio.h>
#include <stdlib.h>
#define SIZE 10
static void
print_array(int *arr, const char *arr_name)
{
int i;
printf("%s = [");
for (i = 0; i < SIZE; i++)
printf("%d%s", arr[i], i < SIZE -1 ? ",":"");
printf("]\n");
}
int main(int argc, char **argv)
{
int i;
int input[SIZE];
int cumsum[SIZE];
for (i = 0; i < SIZE; i++)
{
int _input;
printf("Give me numbers!\n");
fflush(stdout);
scanf("%d", &_input); /* assuming integer */
input[i] = _input;
cumsum[i] = i > 0 ? cumsum[i-1] + _input : _input;
}
print_array(input, "input");
print_array(cumsum, "cumulative");
return 0;
}
or If you'd like to play around with pointers and have a bit more compact version.. perhaps this could be something to study to help you understand pointers, it does the same thing as my code above
#include <stdio.h>
#include <stdlib.h>
#define SIZE 10
static int data[SIZE*2];
int main(int argc, char *argv[])
{
int *input_p = &data[0];
int *cumsum_p = &data[0] + SIZE;
for (; input_p != &data[0] + SIZE; input_p++, cumsum_p++)
{
printf("Give me numbers!\n");
scanf("%d", input_p);
*cumsum_p = input_p == &data[0] ? *input_p : *(cumsum_p-1) + *input_p;
}
}

What is wrong with my hash function?

I'm trying to create a hash table. Here is my code:
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#define N 19
#define c1 3
#define c2 5
#define m 3000
int efort;
int h_table[N];
int h(int k, int i)
{
return (k + i*c1 + i*i*c2) % N;
}
void init()
{
for (int i = 0; i < N; i++)
h_table[i] = -1;
}
void insert(int k)
{
int position, i;
i = 0;
do
{
position = h(k, i);
printf("\n Position %d \n", position);
if (h_table[position] == -1)
{
h_table[position] = k;
printf("Inserted :elem %d at %d \n", h_table[position], position);
break;
}
else
{
i += 1;
}
} while (i != N);
}
void print(int n)
{
printf("\nTable content: \n");
for (int i = 0; i < n; i++)
{
printf("%d ", h_table[i]);
}
}
void test()
{
int a[100];
int b[100];
init();
memset(b, -1, 100);
srand(time(NULL));
for (int i = 0; i < N; i++)
{
a[i] = rand() % (3000 + 1 - 2000) + 2000;
}
for (int i = 0; i < N ; i++)
{
insert(a[i]);
}
print(N);
}
int main()
{
test();
return 0;
}
Hash ("h") function and "insert" function are took from "Introduction to algorithms" book (Cormen).I don't know what is happening with the h function or insert function. Sometimes it fills completely my array, but sometimes it doesn't. That means it doesn't work good. What am I doing wrong?
In short, you are producing repeating values for position often enough to prevent h_table[] from being populated after only N attempts...
The pseudo-random number generator is not guaranteed to produce a set of unique numbers, nor is your h(...) function guaranteed to produce a mutually exclusive set of position values. It is likely that you are generating the same position enough times that you run out of loops before all 19 positions have been generated. The question how many times must h(...) be called on average before you are likely to get the value of an unused position? should be answered. This may help to direct you to the problem.
As an experiment, I increased the looping indexes from N to 100 in all but the h(...) function (so as not to overrun h_table[] ). And as expected the first 5 positions filled immediately. The next one filled after 3 more tries. The next one 10 tries later, and so on, until by the end of 100 tries, there were still some unwritten positions.
On the next run, all table positions were filled.
2 possible solutions:
1) Modify hash to improve probability of unique values.
2) Increase iterations to populate h_table
A good_hash_function() % N may repeat itself in N re-hashes. A good hash looks nearly random in its output even though it is deterministic. So in N tries it might not loop through all the array elements.
After failing to find a free array element after a number of tries, say N/3 tries, recommend a different approach. Just look for the next free element.

C factorial Table (1!-5!) Using For Loop

This my first post on here. I'd like to ask about a problem that I am trying to do for homework.
I'm supposed to be constructing a for loop for the "first 5 factorials" and display results as a table. I followed an example in the book, and I have my for loop and my operations set up, but I don't know what to do to produce the loop in the table. Here is my program:
#include <stdio.h>
int main(void) {
//Problem: Display a range for a table from n and n^2, for integers ranging from 1-10.
int n, factorialnumber, i;
printf("TABLE OF FACTORIALS\n");
printf("n n!\n");
printf("--- -----\n");
for (n = 1; n <= 10; n++) {
factorialnumber = factorialnumber * n;
printf("\n %i = %i", factorialnumber, n);
}
return 0;
}
I know the printf here is wrong. What would I type?
BTW, I'm using codeblocks.
The problem is that you didn't initialize the variables (e.g. factorialnumber). If it has an initial value of 6984857 let's say, the whole algorithm would be messed up.
Try this :
#include <stdio.h>
int main(void) {
//Problem: Display a range for a table from n and n^2, for integers ranging from 1-10.
int i, factorialnumber = 1;
int n = 10; // Max number to go through
printf("TABLE OF FACTORIALS\n");
printf("i i!\n");
printf("--- -----\n");
for (i = 1; i <= n; i++) {
factorialnumber *= i;
printf("%d! = %d\n", i, factorialnumber);
}
return 0;
}

Online judgeProblem (Wrong Answer)

problem in Light OJ:
1001 - Opposite Task:
This problem gives you a flavor the concept of special judge. That means the judge is smart enough to verify your code even though it may print different results. In this problem you are asked to find the opposite task of the previous problem.
To be specific, I have two computers where I stored my problems. Now I know the total number of problems is n. And there are no duplicate problems and there can be at most 10 problems in each computer. You have to find the number of problems in each of the computers.
Since there can be multiple solutions. Any valid solution will do.
Input:
Input starts with an integer T (≤ 25), denoting the number of test cases.
Each case starts with a line containing an integer n (0 ≤ n ≤ 20) denoting the total number of problems.
Output:
For each case, print the number of problems stored in each computer in a single line. A single space should separate the non-negative integers.
Sample Input
Output for
Sample Input:
3
10
7
7
Sample output:
0(space)10
0(space)7
1(space)6
my code :
#include<stdio.h>
#include <stdlib.h>
int main()
{
int c,sum;
int i,j,mini=0,maxi;
int com1,com2;
do{
scanf("%d",&c);
}while (c>25);
int t[c+1];
for(i=1; i<=c; i++)
{
do{
scanf("%d",&t[i]);
}while (t[i]>20);
}
for(i=1; i<=c; i++)
{
maxi=t[i];
com1=rand() % (maxi - mini + 1) + mini;
com2=t[i]-com1;
printf("%d %d\n",com1,com2);
}
return 0;
}
When I submit my code the judge gives wrong answer.
But while I compile the code in CodeBlocks it gives right answer.
I can't understand the problem in online judge.
How can I solve it.
The original post has mini=0 for all cases, but where the total problems is > 10 that may not work. I have adjusted that
#include<stdio.h>
#include <stdlib.h>
int main()
{
int c = 0, mini, maxi, i, com1, com2, *t;
scanf ("%d",&c);
t = malloc (c * sizeof(int));
for (i=0; i<c; i++)
scanf ("%d", &t[i]);
printf("\n");
for (i=0; i<c; i++) {
if (t[i]>10) {
maxi = 10;
mini = t[i] - 10;
} else {
maxi = t[i];
mini = 0;
}
com1 = rand() % (maxi - mini + 1) + mini;
com2 = t[i] - com1;
printf("%d %d\n",com1,com2);
}
free (t);
return 0;
}
Please note that results of malloc() and scanf() have not been checked: they should be.
You seem to be looping unnecessary number of times for the input. I have removed the unnecessary loops from your code while retaining the logic you used. I made a silly mistake with my earlier answer.
#include<stdio.h>
#include <stdlib.h>
int main()
{
int c = 0;
int maxi=10;
scanf("%d",&c);
int t[c];
for(int i=0; i<c; i++)
scanf("%d",&t[i]);
for(int i=0; i<c; i++)
{
int com1 = t[i],com2 = 0;
if (t[i] > 10)
{
com1 = 10
com2 = t[i]-com1;
}
printf("%d %d\n",com1,com2);
}
return 0;
}

function to perform bubble sort in C providing unstable results

I am participating in Harvard's opencourse ware and attempting the homework questions. I wrote (or tried to) write a program in C to sort an array using bubble sort implementation. After I finished it, I tested it with an array of size 5, then 6 then 3 etc. All worked. then, I tried to test it with an array of size 11, and then that's when it started bugging out. The program was written to stop getting numbers for the array after it hits the array size entered by the user. But, when I tested it with array size 11 it would continuously try to get more values from the user, past the size declared. It did that to me consistently for a couple days, then the third day I tried to initialize the array size variable to 0, then all of a sudden it would continue to have the same issues with an array size of 4 or more. I un-did the initialization and it continues to do the same thing for an array size of over 4. I cant figure out why the program would work for some array sizes and not others. I used main to get the array size and values from the keyboard, then I passed it to a function I wrote called sort. Note that this is not homework or anything I need to get credit, It is solely for learning. Any comments will be very much appreciated. Thanks.
/****************************************************************************
* helpers.c
*
* Computer Science 50
* Problem Set 3
*
* Helper functions for Problem Set 3.
***************************************************************************/
#include <cs50.h>
#include <stdio.h>
#include "helpers.h"
void
sort(int values[], int n);
int main(){
printf("Please enter the size of the array \n");
int num = GetInt();
int mystack[num];
for (int z=0; z < num; z++){
mystack[z] = GetInt();
}
sort(mystack, num);
}
/*
* Sorts array of n values.
*/
void
sort(int values[], int n)
{
// this is a bubble sort implementation
bool swapped = false; // initialize variable to check if swap was made
for (int i=0; i < (n-1);){ // loops through all array values
if (values[i + 1] > values [i]){ // checks the neighbor to see if it's bigger
i++; // if bigger do nothing except to move to the next value in the array
}
else{ // if neighbor is not bigger then out of order and needs sorting
int temp = values[i]; // store current array value in temp variable for swapping purposes
values[i] = values[i+1]; //swap with neighbor
values[i+1] = temp; // swap neighbor to current array value
swapped = true; // keep track that swap was made
i++;
}
// if we are at the end of array and swap was made then go back to beginning
// and start process again.
if((i == (n-1) && (swapped == true))){
i = 0;
swapped = false;
}
// if we are at the end and swap was not made then array must be in order so print it
if((i == (n-1) && (swapped == false))){
for (int y =0; y < n; y++){
printf("%d", values[y]);
}
// exit program
break;
}
} // end for
// return;
}
You can easily use 2 nested for loops :
int i, j, temp ;
for ( i = 0 ; i < n - 1 ; i++ )
{
for ( j = 0 ; j <= n - 2 - i ; j++ )
{
if ( arr[j] > arr[j + 1] )
{
temp = arr[j] ;
arr[j] = arr[j + 1] ;
arr[j + 1] = temp ;
}
}
}
also you should now it's a c++ code not a c, because c doesn't have something like :
int mystack[num];
and you should enter a number when you're creating an array and you can't use a variable (like "int num" in your code). This is in C, but in C++ you're doing right.
The first thing to do when debugging a problem like this is ensure that the computer is seeing the data you think it should be seeing. You do that by printing out the data as it is entered. You're having trouble with the inputs; print out what the computer is seeing:
static void dump_array(FILE *fp, const char *tag, const int *array, int size)
{
fprintf(fp, "Array %s (%d items)\n", tag, size);
for (int i = 0; i < size; i++)
fprintf(fp, " %d: %d\n", i, array[i]);
}
int main(void)
{
printf("Please enter the size of the array \n");
int num = GetInt();
printf("num = %d\n", num);
int mystack[num];
for (int z = 0; z < num; z++)
{
mystack[z] = GetInt();
printf("%d: %d\n", z, mystack[z]);
}
dump_array(stdout, "Before", mystack, num);
sort(mystack, num);
dump_array(stdout, "After", mystack, num);
}
This will give you direct indications of what is being entered as it is entered, which will probably help you recognize what is going wrong. Printing out inputs is a very basic debugging technique.
Also, stylistically, having a function that should be called sort_array_and_print() suggests that you do not have the correct division of labour; the sort code should sort, and a separate function (like the dump_array() function I showed) should be used for printing an array.
As it turns out the reason why it was doing this is because when comparing an array's neighbor to itself as in:
if (values[i + 1] > values [i])
The fact that I was just checking that it is greater than, without checking if it is '=' then it was causing it to behave undesirably. So if the array is for example [1, 1, 5, 2, 6, 8] then by 1 being next to a 1, my program did not account for this behavior and acted the way it did.

Resources