I wrote a program
#include<stdio.h>
int *sqrt(int a[10]);
int main()
{
int a[10],i,*b;
printf("enter your integers \n");
for(i=0;i<10;i++)
scanf("%d",a+i);
b=sqrt(a[10]);
printf("the modulus of this values are\n");
printf("%d",*(b));
return 0;
}
int *sqrt(int x[10])// function
{
int *c,i;
for(i=0;i<10;i++)
{
x[i]=x[i]*x[i];
}
c=x;
return p;
}
The code gives me a segmentation fault after I enter the values. What mistake have I made here?
You are passing the 11th element to sqrt():
b = sqrt(a[10]);
You want to pass the address of the 1st element:
b = sqrt(&a[0]);
or even more straight forward:
b = sqrt(a);
Using the construct above the array a decays to a pointer to its 1st element, which is the same as &a[0].
Related
Im trying to understand pointers as function parameters, and in one of the programs there is a segmentation error I can't fix. Firstly, why to use pointers in function arguments? and Why is this error showing?
#include <stdio.h>
void square_it(int* a)
{
printf("The final value is: %d\n", *a * *a);
}
int main()
{
int* input;
puts("This program squares the input integer number");
puts("Please put the number:");
scanf("%d", &input);
square_it(input);
return 0;
}
int* input; does not allocate memory for an int. It mearly makes it possible to make input point at an int (allocated elsewhere). Currently, by dereferencing it (like you do with *a), you make your program have undefined behavior. If you really want an intermediate pointer variable for this, this example shows how it could be done:
#include <stdio.h>
void square_it(int *a) {
*a *= *a; // same as *a = *a * *a;
}
int main() {
int data;
int* input = &data; // now `input` points at an `int`
puts("This program squares the input integer number");
puts("Please put the number:");
// check that `scanf` succeeds:
if(scanf("%d", input) == 1) { // don't take its address, it's a pointer already
square_it(input);
// since `input` is pointing at `data`, it's actually the value of `data`
// that is affected by `scanf` and `square_it`, which makes the below work:
printf("The final value is: %d\n", data);
}
}
Without an intermediate pointer variable:
#include <stdio.h>
void square_it(int *a) {
*a *= *a;
}
int main() {
int input; // note that it's not a pointer here
puts("This program squares the input integer number");
puts("Please put the number:");
if(scanf("%d", &input) == 1) { // here, taking the address of `input` makes sense
square_it(&input); // and here too
printf("The final value is: %d\n", input);
}
}
Without any pointers at all, it could look like this:
#include <stdio.h>
int square_it(int a) {
return a * a;
}
int main() {
int input;
puts("This program squares the input integer number");
puts("Please put the number:");
if(scanf("%d", &input) == 1) { // here, taking the address of `input` makes sense
int result = square_it(input);
printf("The final value is: %d\n", result);
}
}
This is the working code:
#include <stdio.h>
void square_it(int* a)
{
printf("The final value is: %d\n", *a * *a);
}
int main()
{
int i = 0;
int* input = &i;
puts("This program squares the input integer number");
puts("Please put the number:");
scanf("%d", input);
square_it(input);
return 0;
}
There are some errors in the original code:
According to the man-pages to scanf, it takes a format string and then the address of where to store the input.
You gave it the address of a pointer (eg. an int**), which is not what scanf expects.
Also you need to provide memory to store the input in. The scanf string tells that you want an integer as input. In the above code snippet that is i.
input points to i, so i can give the int*, that is input to scanf. scanf will then write into i. We can then go ahead and put the address of i into the sqare_it function.
Since we did not use the heap, we don't need to worry about memory management.
why am i getting this warning?the output was right as i wanted.this ia a simple pointer practice.But i am getting the unwanted warning.please help.
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<time.h>
main()
{
int a,b,c,i,j,k=0;
scanf("%d%d", &a, &b);
int arr[a][b];
int *ptr[b];
ptr[b]=arr;
for(i=0;i<a;i++)
{
for(j=0;j<b;j++)
{
*(*(arr+i)+j)=k;
k++;
}
}
for(i=0;i<a;i++)
{
for(j=0;j<b;j++)
{
printf("%d\t",*(*(arr+i)+j));
}
printf("\n");
}
return 0;
}
Because an array int [a][b] (2D int array) is not a compatible type with int* (int pointer). A 2D array when used in an expression decays to a pointer to the first element, which in this case would be an array pointer to a 1D array, of type int(*)[b].
The line ptr[b]=arr; therefore makes no sense and it also access the array ptr out of bounds.
If you wish to have a pointer to the first item in the 2D array, you would have to type
ptr[n] = &arr[0][0]; // where n is a value that makes sense
yes,I have figured it out.Now,i understand my mistake.
int* ptr[b];
ptr[b]=arr;
is totally wrong.In here I was declaring an array of "ptr" which is pointer to integer and was assigning a pointer "arr" to "ptr[b]" which is pointer to integer.as, arr is a 2D array it returns the address of arr[0][0] .but
ptr[b] is pointer to integer.so,these are not the same.(Actually,"ptr[b]=arr" doesn't make any sense.at first,I didn't understood it enough but now I have fixed it.
int (*ptr)[b];
ptr=arr;
Now it works without any warning.
I have changed the code as the following listing:
#include<stdio.h>
#include<string.h>
#include<stdlib.h>
#include<time.h>
int main()
{
int a,b,i,j;
scanf("%d%d", &a, &b);
int *arr[a][b];
int *ptr[b];
int *k = 0;
ptr[b]=arr[a][b];
printf("\n%s%p","pointer = ",ptr[b]);
for(i=0;i<a;i++)
{
for(j=0;j<b;j++)
{
*(*(arr+i)+j)=k;
k++;
}
}
for(i=0;i<a;i++)
{
for(j=0;j<b;j++)
{
printf("%p\t",*(*(arr+i)+j));
}
printf("\n");
}
return 0;
}
I am working on a project that requires me to read user inputs as pairs of integers and then store them in an array. So, I have created a function that does this. However, I for some reason get a segmentation fault everytime the last input is entered. Here is my code:
int userInput(int *arrayPtr){
int numberPairs, i, numberElements;
printf("%d", sizeof(int));
printf("How many pairs of integers? ");
scanf("%d", &numberPairs);
numberElements = numberPairs*2;
arrayPtr = malloc((numberElements*sizeof(int)) + 64);
for(i = 0; i < numberElements; i+=2){
int first,second;
printf("\nEnter pair: ");
printf("Before scanf");
scanf("%d %d", &first, &second);
printf("%d", first);
arrayPtr[i] = first;
arrayPtr[i+1] = second;
}
printf("%d", numberPairs);
return numberPairs;
}
Here is how I call the function:
int main(){
int *arrayPtr, numberPairs;
numberPairs = userInput(arrayPtr);
multiplyPairs(arrayPtr, numberPairs);
free(arrayPtr);
}
At the moment, I am mainly trying to make the for loop execute in its entirety, but for some reason it always seg faults on the last iteration. For example, if my input for the pairs was 1 2, 3 4, 5 6, my ouput would be 1 3 and then a seg fault (this output is referring to the print statement in the for loop). I have spent a few hours trying to debug this code as well as having other students look at it, and I can not figure out what is wrong. If you could point me in the right direction I would greatly appreciate it. Thanks.
UPDATE: I copied and pasted the code into a new file and it works as intended. Thank you to everyone who told me about other elements of my code that were wrong.
You need this:
int userInput(int **arrayPtr){
int numberPairs, i, numberElements;
printf("%d", sizeof(int));
printf("How many pairs of integers? ");
scanf("%d", &numberPairs);
numberElements = numberPairs*2;
*arrayPtr = malloc((numberElements*sizeof(int)) + 64);
for(i = 0; i < numberElements; i+=2){
int first,second;
printf("\nEnter pair: ");
printf("Before scanf");
scanf("%d %d", &first, &second);
printf("%d", first);
(*arrayPtr)[i] = first;
(*arrayPtr)[i+1] = second;
}
printf("%d", numberPairs);
return numberPairs;
}
int main(){
int *arrayPtr, numberPairs;
numberPairs = userInput(&arrayPtr);
multiplyPairs(arrayPtr, numberPairs);
free(arrayPtr);
}
Explanation using a very simple example
You want to write a function that mutiplies the first with it's second argument and stores the value in the third agrument.
So you try this:
void Multiply(int a, int b, int r)
{
r = a * b;
}
int main(){
int result = 0;
Multiply(3, 4, result);
printf ("result = %d\n", result);
return 0;
}
And you expect the output is result = 12. But you get result = 0. The reason is that when a function parameter is modified, the function argument of the caller won't be modified because the parameters are passed by value (it's like that in C and in most other programming languages). BTW what should happen if you dont pass a variable as 3rd argument but a constant: for example Multiply(3, 4, 5); ?
If you want your function to modify an argument, you have to pass a pointer to the argument to the fonction and modify the pointed value in the function:
Following example shows what to do:
void Multiply(int a, int b, int *r)
{
// r points to the variable passed as third argument
*r = a * b;
}
int main(){
int result = 0;
// here we pass the pointer to result
Multiply(3, 4, &result);
printf ("result = %d\n", result);
return 0;
}
the following code crashes if i give array of pointer here is there any other way to accept value through array of pointers or did i do somethong wrong here
the run this program after compiling you should type
objectname -numberoflines
//program to print first n lines of string using command line arguement
#include<stdio.h>
#include<ctype.h>
#include<stdlib.h>
#include<string.h>
int less(int x,int y);`enter code here`
int main(int argc,char* argv[])
{
int i,j,n,num;
char *lines[100];/*if I use two dimensional array here the code compiles
char nu[6];
// the whole for loop is for checking error in n
for(i=1,n=strlen(argv[1]);i<n;i++)
{
if(argv[1][i]=='.')
{
printf("your input was not correct \n");
return 0;
}
if(argv[1][i]=='-')
{
printf("your input was not correct \n");
return 0;
}
if(isalpha(argv[1][i])!=0)
{
printf("your input was not correct indeed");
return 0;
}
}
printf("\t\t application to print number of last n lines \n\n\n");
printf("enter the number of lines\n");
scanf("%d",&n);
printf("enter your lines \n");
for(j=0;(n<100)&&(j<=n);j++)
{
gets(lines[j]);
}
strcpy(nu,argv[1]);
nu[0]=' ';
num=atoi(nu);
num=(less(num,n));
for(i=0;i<=num;i++)
{
printf("%s",lines[i]);
}
return 0;
}
int less(int x,int y)
{
int z;
return (z=(x>y?y,printf("your input lines are less\n"):x));
}
The main problem is that when you write
char *lines[100];
You create an array of 100 char* pointers. These pointers have no memory allocated for them and they point to a random location. Writing to that location(using gets in your program) invokes Undefined Behavior.
To fix it, allocate memory for each pointer using
for(i=0 ; i<100 ; i++)
lines[i]=malloc(AMOUNT_OF_BYTES_TO_ALLOCATE);
And later, after the use is over, free the allocated memory using
for(i=0 ; i<100 ; i++)
free(lines[i]);
The reason that it worked when you used a two dimensional array is that you create an array of array of char for which memory is automatically allocated in the stack.
Though we declare a function with an integer array, we pass address of the array to the function. In the case of simple integers it gives error if we pass address we get pointer conversion error. But how its possible in case of an array
#include<stdio.h>
void print_array(int array[][100],int x, int y);
main()
{
int i,j,arr[100][100];
printf("Enter the array");
for(i=0;i<2;i++)
{
for(j=0;j<2;j++)
{
scanf("%d",&arr[i][j]);
}
}
print_array(arr,i,j);
}
void print_array(int array[][100],int x,int y)
{
int i,j;
printf("\nThe values are\n");
for(i=0;i<x;i++)
{
for(j=0;j<y;j++)
{
printf("%d",array[i][j]);
}
}
}
My question is even though our function is declared as one with integer array as first parameter (here) we are passing array address when we call the function. How does it function?
Your are passing the array, not its address.
arr is an int[][] array
(in fact it is pretty the same as &(arr[0]), which is a pointer to (the address of) the first line of your array. In C, there is no practical difference between an array and the corresponding pointer, except you take it's address with the & operator.)
Edit: Ok, just to make me clear:
#include <stdio.h>
int fn(char p1 [][100], char (*p2)[100])
{
if (sizeof(p1)!=sizeof(p2))
printf("I'm failed. %i <> %i\n",sizeof(p1),sizeof(p2));
else
printf("Feeling lucky. %i == %i\n",sizeof(p1),sizeof(p2));
}
int main()
{
char arr[5][100];
char (*p)[100]=&(arr[0]);
fn(arr, arr);
fn(p, p);
return 0;
}