3
#include <stdio.h>
struct invent
{
   char name[20];
   int number;
   float price;
};

int main()
{
   char ch;
   struct invent product[3],*ptr;
   printf("INPUT\n\n");
   for(ptr=product;ptr<product+3;ptr++)
      scanf("%s %d %f",ptr->name,&ptr->number,&ptr->price);

   printf("\nOUTPUT\n\n");
   ptr=product;
   while(ptr<product+3)
   {
      printf("%20s %5d %10.2f\n",ptr->name,ptr->number,ptr->price);
      ptr++;
   }

   return 0;
}

Why in scanf function for entering name only ptr->name is used while entering number and price &ptr->number, &ptr->price is used. I want to ask why we are using & at all because ptr is itself storing the address of structure. Here is another code to explain

int main()
{
    int a,*p;
    p=&a;
    scanf("%d",p);
    printf("%d",a);
    return 0;
}

In the above code we are not using &p in scanf function because p is itself storing the address of a, so why use &ptr->number and &ptr->price for structures.

R Sahu
  • 204,454
  • 14
  • 159
  • 270
Rajesh Shaw
  • 547
  • 1
  • 4
  • 9

1 Answers1

2

Why in scanf function for entering name only ptr->name is used while entering number and price &ptr->number,&ptr->price

Because ptr->name is an array and an array's name, in an expression, gets converted into a pointer to its first element. Hence, there's no & (address-of) used when passing it to scanf() and using &ptr->name would be wrong. But other scalar types don't have such "decaying" property. Hence, & is used.

See: What is array decaying? In your second program, p is already a pointer. So, passing &p would be int** whereas scanf() expects an int* for the format specifier %d.

Basically, in both cases you are required to pass pointers (char* for %s and int* for %d). But in the case of arrays, the pointer is automagically derived as per the rules of the C standard.

Also relevant: http://c-faq.com/aryptr/aryvsadr.html

Community
  • 1
  • 1
P.P
  • 117,907
  • 20
  • 175
  • 238
  • which has higher precedence & or -> – Rajesh Shaw Oct 07 '16 at 15:48
  • 2
    `->` (dereferencing) binds tighter than `&`(address-of). `&ptr->name` is equivalent to `&(ptr->name)`. – P.P Oct 07 '16 at 16:01
  • why (*ptr).number is same as ptr->number – Rajesh Shaw Oct 07 '16 at 16:06
  • 1
    C standard defines they are equivalent. The reason is probably historical and also for ease of use. Consider a struct contain pointer to another struct can be written as `p->q->value`. Writing the same using `*` is more cumbersome. – P.P Oct 07 '16 at 16:29