1

I am testing passing of struct array argument in struct function "push" but getting an error message of

"passing 'shelf' (aka 'struct shelf') to the parameter of incompatible type 'shelf *' (aka 'struct shelf *');".  

How can I fix this error? I don't know what needs to be done in order to make it work. I have declared the structs and push function in the header file.

Main purpose of this program is to access the values of book struct in shelf struct.

Here are my code snippets.

header file

#ifndef __POINTERS_H_
#define __POINTERS_H_

typedef struct book
{
    char *b_title;
    int b_pages;
}book;

typedef struct shelf
{
    char *s_title;
    int s_pages;
}shelf;

book book_details[100];
shelf shelf_item[100];

shelf push(shelf item[100]);


#endif // __POINTERS_H_

c file:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "pointers.h"

int main(void)
{
    book book_details[100];
    shelf shelf_item[100];

    book_details[0].b_title = "c++";
    book_details[0].b_pages = 200;

    push(shelf_item[0]);
    printf("Shelf Item's title is: %s\n", shelf_item[0].s_title);
    printf("Shelf Item's title is: %i\n", shelf_item[0].s_pages);

    return 0;
}

shelf push(shelf item[100])
{
    strcpy(item[0].s_title, book_details[0].b_title);
    item[0].s_pages = book_details[0].b_pages;

    return item[0];
}
7
  • And your question is? Commented Jul 2, 2020 at 22:34
  • 1
    __POINTERS_H_ identifiers with double underscores are reserved by C standard. Don't use them in your code. Commented Jul 2, 2020 at 22:34
  • 1
    @AndrewHenle I have modified the question. Sorry for the inconvenience. Commented Jul 2, 2020 at 22:36
  • @KamilCuk I haven't used double underscores in my code. Maybe you are referring to is the header in the header file and that's pre-defined. Commented Jul 2, 2020 at 22:38
  • This is C. You can't return a shelf, only a shelf*. And you can't pass an array with 100 elements to a function. Only a pointer to an array. And the message is clear: You can't pass a shelf to a function because it is a struct. You can only pass shelf* to a function. Commented Jul 2, 2020 at 22:44

2 Answers 2

2

1. The arguments do not match.

shelf item[100] when passed as an argument will decay to shelf *item.

As you are passing a shelf object as an argument(the first element of the array), that won't work.


2. Note that this statement:

book_details[0].b_title = "c++"

Leads to undefined behavior, b_title struct member is an uninitialized pointer, as is s_title, you cannot store anything in it until it points to a valid memory location, alternatively you can use a char array:

char b_title[100];

And

char s_title[100];

To assign a string to it you then need to use strcpy or a similar method.


3. There is also the fact that you declare book book_details[100]; and shelf shelf_item[100]; twice, at global scope and again in main.


Assuming global shelf_item and book_detais arrays you can do something like:

Header

typedef struct book {
    char b_title[100]; //b_title as char array, alternatively you can allocate memory
    int b_pages;
}book;

typedef struct shelf {
    char s_title[100]; //s_title as char array
    int s_pages;
}shelf;

book book_details[100];
shelf shelf_item[100];

void push(); //as shelf is global there is no need to pass it as an argument

C file

int main(void) {
    strcpy(book_details[0].b_title ,"c++"); //strcpy
    book_details[0].b_pages = 200;

    push();

    printf("Shelf Item's title is: %s\n", shelf_item[0].s_title);
    printf("Shelf Item's title is: %i\n", shelf_item[0].s_pages);
    return 0;
}

void push() {
    strcpy(shelf_item[0].s_title, book_details[0].b_title);
    shelf_item[0].s_pages = book_details[0].b_pages;
}

Assuming local shelf_item and book_detais arrays you can do something like:

Header

#define SIZE 100

typedef struct book {
    char *b_title;
    int b_pages;
}book;

typedef struct shelf {
    char *s_title;
    int s_pages;
}shelf;

void push(book *b, shelf *s); //pass both arrays as arguments

C file

int main(void) {

    book book_details[SIZE];
    shelf shelf_item[SIZE];

    book_details[0].b_title = malloc(SIZE); //allocate memory for b_title
 
    if(book_details[0].b_title == NULL){ /*deal with error*/}

    strcpy(book_details[0].b_title ,"c++");
    book_details[0].b_pages = 200;

    push(book_details, shelf_item);

    printf("Shelf Item's title is: %s\n", shelf_item[0].s_title);
    printf("Shelf Item's title is: %i\n", shelf_item[0].s_pages);
    return 0;
}

void push(book *b, shelf *s) {

    s[0].s_title =  malloc(SIZE); //allocate memory for s_title
    if(s[0].s_title == NULL){ /*deal with error*/}

    strcpy(s[0].s_title, b[0].b_title);
    s[0].s_pages = b[0].b_pages;
}
Sign up to request clarification or add additional context in comments.

6 Comments

Are you sure that it is a good thing to provide a complete solution for the home exercise? ;-)
@reichhart, maybe a got carried away, I still think these are just relatively small fixes to the OP original program, I wouldn't call it a solution to the exercise.
@anastaciu thanks for explaining each and everything in much much detail. It's not an assignment, I am new at learning c language and was practicing different ways of using structs. I studied different books but the way you explained is so comprehensive. You can write your own book and i ll be the first one to buy it.
@OwaisQayum, I appreciate your words, I'll consider your advice, at least one copy will be sold I guess :)
@anastaciu I just wanted to prevent that you do even more. ;-) Nevermind, you got my upvote.
|
2

There are several issues. Here's the first one which causes the issue:

push(shelf_item[0]);

The error message is that you are passing shelf while shelf * is expected (array). Simply pass the address of the item (the start of the array): &shelf_item[0]

The prototype

shelf push(shelf item[100]);

does not make any sense if you just want to push one item.

Also

book book_details[100];
shelf shelf_item[100];

are declared twice.

And it is "bad style" (TM) if a function got only one argument passed but uses a hidden/global variable to also work on.

And your print statement does not print the values of the returned item.

1 Comment

I have made many mistakes and after reading your feedback things are much clearer now.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.