PDA

View Full Version : Call by value is not working properly



c2tarun
December 18th, 2010, 02:41 PM
I was trying to solve this problem:
http://www.codechef.com/problems/MIXTURES/

this is my code:


#include<stdio.h>
#include<string.h>

char words[100000][2];
int n; // number of words

int sum(int* p)
{
int s=0,i;
for(i=0;i<n;i++)
s+=*(p+i);
return s;
}

int func(int c, int check[])
{
int i;
check[c]=1;
if(sum(&check[0]) != n)
{
for(i=0;i<n;i++)
{
if(check[i] == 0 && words[c][1] == words[i][0] )
{
func(i,check);
// check[i]=0;
}
}
}
else
{
if(sum(&check[0]) == n)
return 1;
else
return 0;
}
return 0;
}

int main(void)
{
char *temp=NULL;
size_t strn=1000;
int t; // number of test cases
int check[100000];
int templen;
int i; // loop variable
memset(check,0,sizeof(check));
getline(&temp,&strn,stdin);
t=atoi(temp);
while(t--)
{
getline(&temp,&strn,stdin);
n=atoi(temp);
for(i=0;i<n;i++)
{
getline(&temp,&strn,stdin);
templen=strlen(temp);
words[i][0]=*temp;
words[i][1]=*(temp+templen-2);
}

for(i=0;i<n;i++)
{
if(func(i,check) == 1)
break;
}
if(i<n)
printf("Ordering is possible.\n");
else
printf("The door cannot be opened.\n");
}
return 0;
}

I don't know exactly what is wrong with my code.
check is a local variable to main, but I am copying check of main to a local check of function 'func'. problem is, i am only changing the value of local check of 'func' but that change is also reflected in main. Can anyone please tell me what is wrong in my code.
thanks

MadCow108
December 18th, 2010, 03:15 PM
your not copying it, you fell for one of the quirks of C:
int func(int c, int check[])
is the same as:
int func(int c, int * check)

so you pass the pointer to the original array and modify it

you need to explicitly copy it before or in the function e.g. by memcpy

saulgoode
December 18th, 2010, 03:26 PM
I don't know exactly what is wrong with my code.
check is a local variable to main, but I am copying check of main to a local check of function 'func'. problem is, i am only changing the value of local check of 'func' but that change is also reflected in main. Can anyone please tell me what is wrong in my code.

Arrays are always passed by reference in C. This is because at compile time, the size of an array may not be known (whereas the size of structs, floats, ints, etc are fixed).

So when your 'func()' executes "check[c]=1", you are actually modifying main's local variable.

trent.josephsen
December 18th, 2010, 03:47 PM
int sum(int* p)
{
int s=0,i;
for(i=0;i<n;i++)
s+=*(p+i);
return s;
}
It would be better to pass n into this function rather than depending on a global variable. Also, why *(p+i) instead of p[i]?




if(sum(&check[0]) != n)



if(sum(&check[0]) == n)


In other words, sum(check).

Also, getline isn't part of the C standard -- #include <getline.h> to use it with a conforming toolchain that supplies it.

c2tarun
December 18th, 2010, 05:27 PM
Arrays are always passed by reference in C. This is because at compile time, the size of an array may not be known (whereas the size of structs, floats, ints, etc are fixed).

So when your 'func()' executes "check[c]=1", you are actually modifying main's local variable.
is there any was so that we can pass array by call by value??

Arndt
December 18th, 2010, 05:34 PM
is there any was so that we can pass array by call by value??

You can put it inside a struct. But if it's large, this is not a good idea, since it is put on the stack, and stack space is not guaranteed to be very large.

I don't know what you want to do, but a usually better way is to make a copy and pass a pointer to the copy (or pass the original and let the callee do the copying, whichever is most suitable).

c2tarun
December 18th, 2010, 06:09 PM
You can put it inside a struct. But if it's large, this is not a good idea, since it is put on the stack, and stack space is not guaranteed to be very large.

I don't know what you want to do, but a usually better way is to make a copy and pass a pointer to the copy (or pass the original and let the callee do the copying, whichever is most suitable).


I think i'll let the callee do the copying :)