A weird output? - c

I am new to the C.Sc course and we are taught C program.
I was trying some of the basic stuff. Currently I am learning User-Defined-Function.
The following code is the one I was trying with. I know it is pretty simple but I am not able to understand why it is producing such weird output.
#include <stdio.h>
int add(int a); //function declaration
int main (void)
{
int b,sum;
printf("\nEnter a number: ");
scanf("%d", &b);
sum = add(b); //function calling
printf("\nSum: %d\n\n", sum);
}
int add(int a) //function definition
{
int result;
for(int i = 0; i < a; i++)
{
result = result + i;
return result;
}
}
The output for 1 is 32743
The output for 2 is 32594
The output for 3 is 32704
The weird thing is output change each time for the same number.
It's just weird considering my experience in C.Sc. till date. Kindly explain what the program is doing.
This is the right place to post problems like this. Right?

You forget to initialize result.
int result = 0;
Explanation : If you do not initialize the variable, it will have a "random" number, and then you are going to get "random" output
Also :
You also forgot to return something if a = 0, or a negatif number !
And your main NEED to return a int.
Also, there is no point to do a loop since you return inside of it, you always going to return 0 in the loop.
Here is a correction of your code :
#include <stdio.h>
int add(int a); //function declaration
int main (void)
{
int b,sum;
printf("\nEnter a number: ");
scanf("%d", &b);
sum = add(b); //function calling
printf("\nSum: %d\n\n", sum);
return 1;
}
int add(int a) //function definition
{
int result = 0;
for(int i = 0; i < a; i++)
{
result = result + i;
}
return result;
}
Exemple with 10 as input : https://ideone.com/6BjM6y

You need to initialize result,
int result = 0;
In your code, result is not initialized so at the
result = result + i;
line, you use whatever value result has and it's not possible to determine which value is that because it's a garbage value.
In c, variables are not automatically initialized for performance reason, with a few exceptions, the most notable are
Local variables with static storage class.
Global variables.
when you leave a variable uninitialized, then trying to read it's value is considered undefined behavior.
In response to your comment
The problem is that you return after adding 0 to result which is 0, so move the return result; outside of the for loop and it should work.

You need to initialize the variable result. Since it is bot initialized, the compiler initializes it with a default value, which could be a "funky" mumber. To fix this, initialize result in your Add() function to:
int result = 0;
Another thing: your return statement is inside the for-loop. This means that the for-loop will terminate at the end of the first loop since there is a return statement that will terminate the function. To fix it, change your function to:
int result;
for(int i = 0; i < a; i++)
{
result += i; // shorthand way of writing result = result + i. Same end result
}
return result; // should be outside the loop

Related

how does adding a line of prtintf fix this?

I am new to the C language (I started to learn it a week ago). the program was having some random output so i wanted to see what was it storing in the variable. then the printf fixed it somehow.
#include <stdio.h>
int laske(float lista[]);
const int MAX = 3;
int main()
{
float lista[5], yhteispisteet;
int counter = 0;
do
{
printf("Anna %d. pisteet: \n", counter +1);
scanf("%f", &lista[counter++] );
printf("%d",lista[counter]); <-- if you remove this line it dosent work
}
while (counter < MAX);
yhteispisteet = laske(lista);
printf("\nYhteispisteet ovat: %.2f\n", yhteispisteet);
getchar();
return 0;
}
int laske(float lista[])
{
int rivi, tulos;
for (rivi=0; rivi< MAX; rivi++)
tulos = tulos + lista[rivi];
return tulos;
}
Three things to note from your code:
You are adding a float and an int when you do: tulos = tulos + lista[rivi];, without casting the input float to int like this: tulos = tulos + (int)lista[rivi]; Or better yet, just declare tulos as float, and return a float from your laske function, because the return value is again being assigned to a float yhteispisteet
You assign to lista[counter++] with the scanf, and then increment the counter (post-increment) and print the lista[counter](which is printing the incremented indexed value that did not take any assignments yet). It is better to increment counter++ after the printf function.
You did not initialize your variable tulos, and this gives you undefined behavior when your code is running, which is probably what you are seeing when you add and then remove the printf and then rerun

why are there two outputs for the same c prog below?

#include <stdio.h>
main()
{
int n;
n+=2;
printf("sum=%d", n);
return 0;
}
Here the 'Sum'=2
Another program:-
#include <stdio.h>
main()
{
int n,a=2;
n+=a;
printf("sum=%d", n);
return 0;
}
here the output 'sum' = 3
WHY so?? What is the problem in the code??
This is Undefined Behavior. Using uninitialized variables (n in both snippets) can produce unexpected results, meaning that running the first code twice might produce different outputs. There is no "correct" output for either of the codes, but if you'll set n to a specific value in both codes, you'll start getting consistent results.
This is UB (Undefined Behavior):
main()
{
int n;
printf("sum=%d", n);
return 0;
}
This is not:
main()
{
int n = 0;
printf("sum=%d", n);
return 0;
}
When you don't assign a value to a local variable in C, its value is undefined. So in some cases it will be 0, in some 1, in some, something else entirely. You cannot know what it will be and you should never rely on it. Instead, initialize your local variables:
int n = 0; // initialization
n += 2;
printf("sum=%d", n); // will always print 2

Segmentation fault when trying to add elements of an array

I'm trying to create a function that returns as its result the sum of the elements in the array. When I try to run the program, I get a segmentation fault. Could someone please point me in the right direction? Thank you!
int arraySum (int array[], int numberOfElements) {
int result = 0;
for (int i = 0; i < numberOfElements; i++)
{
result += array[i];
}
return result;
}
int main (void) {
int numberOfElements;
int *array = NULL;
printf("How many elements would you like in your array: ");
scanf("%i", &numberOfElements);
printf("\nPlease list the values of the elements in the array: ");
for (int i = 0; i < numberOfElements; i++)
{
scanf("%i", &array[i]);
}
int result = arraySum(array, numberOfElements);
return result;
}
The problem you have is, that in C you need to manually allocate the memory if you are using a pointer instead of say a fixed-size array.
This is usually done by calling malloc, which will return a void-pointer (void*), which you need to cast to the desired type (in your case (int*)) before assigning it.
It is also important to note, that, when using malloc, you need to specify the amount of Bytes you want to allocate. This means that you can't just call it with the number of integers you want to store inside, but rather have to multiply that number with the amount of Bytes that one integer occupies (which depends on the Hardware and Operating System you use, hence you should use sizeof(int) for that purpose, which evaluates to that size at compile time).
I modified your code with a working example of how it could be done:
#include <stdio.h>
#include <stdlib.h>
int arraySum (int array[], int numberOfElements) {
int result = 0;
int i;
for (i = 0; i < numberOfElements; i++) {
result += array[i];
}
return result;
}
int main(int argc, char **argv) {
int numberOfElements;
int *array = NULL;
printf("How many elements would you like in your array: ");
scanf("%i", &numberOfElements);
array = (int*) malloc(numberOfElements * sizeof(int));
printf("\nPlease list the values of the elements in the array: ");
int i;
for (i = 0; i < numberOfElements; i++) {
scanf("%i", &array[i]);
}
int result = arraySum(array, numberOfElements);
printf("\n\nThe result is: %d\n", result);
return 0;
}
You are also trying to return the result in your main function, but the return value of main in C is used to signal whether your program terminated without errors (signalled by a return value of 0) or didn't encounter any issues (any value other than 0).
You need to allocate memory. It is not enough to just declare a pointer. You do it like this: array=malloc(numberOfElements*sizeof(*array));
Also, although it is possible to return result from the main function, you should not do that. The return value from main is usually used for error checking. Change the end of your program to
printf("Sum: %d\n", result);
return 0;
Returning 0 usually means that no error occurred.

C - can variate location be promoted?

I am new to the language and was trying a simple code. I wanted to try to create a loop based on pointers. but it seems like you can not promote variate location like in assembler. or i just did it wrong? and if i really can't can i force a new variadate to be born in specific location? that was my code
#include <stdio.h>
int main(void) {
int firstnumber = 1;
int *beginning = &firstnumber;
printf("%i %i \n",firstnumber,beginning);
Test1(firstnumber,beginning);
return 0;
}
Test1 (int num, int begin)
{
int reserve = num;
if(num != 100)
{
&num +=2;
num = (reserve+1);
return Test1(num, begin);
}
else
{
int assist = begin;
while(*assist != 100)
{
printf("/n \n %i %i \n /n",num,assist);
&assist += 2;
}
}
}
I know it might look ridiculous but i'm really curious
You're thinking about this backwards. Pointers are the variables you can move around, so use them for anything you want to move around.
firstnumber is an integer variable - the compiler decides where it is stored and you can't tell the compiler to rebind the name firstnumber to a different location. You can, however, move a pointer around as much as you like. So,
void Test1(int num) {
&num +=2;
num = 42;
}
is nonsense, but
void Test2(int *num) {
num += 2;
*num = 42;
}
is fine - so long as num+2 is still a valid allocated object. For example, you could call it like
int i[5];
Test2(i); /* sets i[2] = 42 */
(if you pass in an array of fewer than 3 integers you get a runtime bug rather than a compile error, as Test2 damages your stack frame or other memory it shouldn't be touching).
No, you cannot promote/change variable location.
So this:
int num;
&num +=2;
does not make sense, and will result in an error:
error: lvalue required as left operand of assignment
&num +=2;
^~
Same for:
int assist;
&assist += 2;
Your code will compile only if you modify these statements (but now the logic is changed, you should work on that), but now it will result in an infinite loop, since your function never returns in the else case:
#include <stdio.h>
void Test1 (int num, int* begin);
int main(void) {
int firstnumber = 1;
int *beginning = &firstnumber;
printf("%i %i \n",firstnumber, *beginning);
Test1(firstnumber, beginning);
return 0;
}
void Test1 (int num, int* begin)
{
int reserve = num;
if(num != 100)
{
num +=2;
num = reserve + 1;
return Test1(num, begin);
}
else
{
int assist = *begin;
while(assist != 100)
{
printf("/n \n %i %i \n /n",num,assist);
assist += 2;
}
}
}
Good luck!
OK i checked the code deeper and got several conclusions:
function variable can not inherit his ancestor adress. therefore using a function for the task is useless unless i use some static variable
I had another conclusion but i don't remember what it was. sorry and thank you for your time

How can I get this value from function stored properly?

int num5(int number)
{
number = 5;
return 0;
}
int main()
{
int number;
printf("%d", number);
}
I need my main to be able to store number as 5, im just testing it with print number as 5. I realise with this example i could just do
return number; //function
int number = num5(number); //main
But my program is a bit more complicated and I cant just return number.
You are using Pass by value method. What ever the changes takes places in the function it won't affect in the main program. Those changes are limited with in the function.
You need use the following method to do this!
int num5(int *number)
{
*number = 5;
return 0;
}
int main()
{
int number;
number = num5(&number); // pass the address of the number instead value
printf("%d", number);
}
When you Pass the address of the variable to the function, whatever the changes you are doing in the function, that is retained by that variable. So you will get the latest assigned value!
You could pass a pointer and de-reference it in the function:
int num5(int* pnum)
{
*pnum = 5; // you may want to check that pnum is not NULL
return 0; // presumably you don't always return 0 in real code
}
Then
int number = 42;
printf("%d", number); // prints 42
int ret = num5(&number);
printf("%d", number); // prints 5
As others mentioned, call by reference [a.k.a. call by address] will do the job for you. To be on safer side, don't forget to add a NULL pointer check to your incoming pointer. Also, as per usual convention, main() should return 0 in case of successful completion of execution.
Modified Code:
int num5(int *number)
{
if (number) //NULL check for incoming pointer
{
*number = 5;
}
return 0;
}
int main()
{
int number;
number = num5(&number); // pass the address of the number instead value
printf("%d", number);
return 0; //for convention
}

Resources