struct node * void expected identifier or '(' before 'void' - c

There is a function like this. I took this error expected identifier or '(' before 'void'
How to solve this problem? Thank you.
struct node * void ekleSirali(struct node * r,int x){
if(r==NULL){
r=(struct node *)malloc(sizeof(struct node));
r->next=NULL;
r->x =x;
return r;
}
I don't know whether I should write struct.

The type specifier void is redundant and invalid in this context. Write
struct node * ekleSirali(struct node * r,int x){
That is the function return type can be either void (if the function returns nothing) or struct node * (if the function returns a pointer of the type struct node * as shown in your code snippet).

Related

error: incompatible type for argument 1 of 'push'

I'm tryng to build a linked list, but i can't pass the errors. Somebody can help me undertand what is going on? I already change the type of the structures, but nothing changes.
I'm tryng to build a linked list, but i can't pass the errors. Somebody can help me undertand what is going on? I already change the type of the structures, but nothing changes.
/*gcc -o lista.exe lista.c -Wall -pedantic -Wextra*/
#include <stdio.h>
#include <stdlib.h>
struct list
{
int info;
struct list *next;
};
void push(struct list, int);
int main(int argc, char *argv[])
{
struct list *list;
argc = argc;
argv = argv;
/*Start list*/
list = (struct list *)malloc(sizeof(struct list));
list->info = 5;
list->next = NULL;
push(&list, 70);
return 0;
}
void push(struct list **list, int info)
{
struct list *new;
new = (struct list *)malloc(sizeof(struct list));
new->info = info;
new->next = NULL;
*list->next = new;
}
lista.c: In function 'main':
lista.c:25:3: error: incompatible type for argument 1 of 'push'
lista.c:11:6: note: expected 'struct list' but argument is of type 'struct list **'
lista.c: At top level:
lista.c:30:6: error: conflicting types for 'push'
lista.c:11:6: note: previous declaration of 'push' was here
lista.c: In function 'push':
lista.c:37:8: error: request for member 'next' in something not a structure or union
Your function prototype/declaration for push doesn't match your function definition for push. At the top, change
void push(struct list, int);
to
void push(struct list**, int);
Alternatively, you could erase the function prototype for push and move the definition for it above main. The compiler reads files top to bottom, and so in main when you call push(&list, 70);, the compiler will complain if it doesn't know of a function matching that signature. Since your prototype is wrong, it doesn't see a function matching a return type of void with arguments struct list**, int, so it generates the error that you see.
An aside, I assume you have
argc = argc;
argv = argv;
to suppress warnings from unused variables. If you don't plan to use argc or argv, you can change your main signature to int main(void){ ... } and dispose of them entirely.
The compiler sees the declaration
void push(struct list, int);
after that it encounters this call
push(&list, 70);
where the first argument has the type struct list **. And it issues an error that type of the function parameter struct list and the type of the argument expression struct list ** are not compatible.
The function declaration without definition does not coincide with the function declaration with definition after the function main.
But in any case the function definition is invalid.
This statement within the function
*list->next = new;
is incorrect. It is equivalent to
*( list->next ) = new;
where the pointer list having the type struct list ** points to a pointer not to a structure object. That is the pointed pointer does not have the data member next. And the compiler reports about this
lista.c:37:8: error: request for member 'next' in something not a
structure or union
The function should be declared the following way
int push( struct list **, int );
and defined like
int push( struct list **list, int info )
{
struct list *new_node = malloc( sizeof( struct list ) );
int success = new_node != NULL;
if ( success )
{
new_node->info = info;
new_node->next = *list;
*list = new_node;
}
return success;
}
And in main there is no need to allocate the head node outside the function push.
You should write
int main( void )
{
struct list *list = NULL;
push( &list, 5 );
push( &list, 70 );
return 0;
}

How to free a tree struct using double pointer?

I have to free a tree and set his root to NULL using a particular function. I tried to use a recoursive method. But if I compile i get some warnings about "incompatible pointer type" and I'm not able to resolve it. This is the struct:
typedef struct node {
int key;
struct node *left, *mid, *right;
} node_t;
And here the function. The first line cannot be changed:
void free_tree (node_t ** root){
if(root != NULL){
free_tree((*root)->left);
free_tree((*root)->mid);
free_tree((*root)->right);
free(*root);
}
return;
}
Any help would be appreciated
Your function expected a pointer to a pointer-to-node. You're giving it a pointer-to-node three times in your recursive calls. Further, you're not validating that the pointer-to-pointer, and the pointer it points to, are non-null; you're only validating the former.
In short, your function should look like this:
void free_tree (node_t ** root)
{
if(root && *root)
{
free_tree(&(*root)->left);
free_tree(&(*root)->mid);
free_tree(&(*root)->right);
free(*root);
*root = NULL;
}
}
The last functional line is optional, but frankly it's pointless to do this with pointers-to-pointers unless you're going to do that anyway, as it sets the caller's pointer to NULL after obliterating the tree. Given a properly built tree, your caller should deliver the address of the tree root when destroying the entire tree, as:
node_t *root = NULL;
// ... build tree ...
free_tree(&root);
// root is now NULL; tree is destroyed
Your question cannot be answered very clearly but at least I can tell you why you have this warning about incompatible pointer type :
Your function prototype is
void free_tree (node_t ** root);
It's argument is a node_t **.
Your struct is
typedef struct node {
int key;
struct node *left, *mid, *right;
} node_t;
So in your function :
void free_tree (node_t ** root)
{
if(root != NULL)
{
free_tree((*root)->left); <<< '(*root)->left' is of type 'node_t *'
free_tree((*root)->mid); <<< '(*root)->mid' is of type 'node_t *'
free_tree((*root)->right); <<< '(*root)->right' is of type 'node_t *'
free(*root);
}
return;
}
You call you function giving a node_t * as argument whereas your function expects a node_t **

Array of Structurer in C

I was just brushing my pointer concepts and it seems its really messed up over time.
I was trying to implement BFS in binary tree.
Pseudo Code :
1) tempNode = root node
2) while tempNode is not null
print data at tempNode
enqueue left and right child
tempNode = dequeue
Here's my code :
#include <stdio.h>
#include <stdlib.h>
#define MAX_Q_SIZE 100
/**
* Using Queue to keep track of next nodes to be visited
*/
struct node
{
int data;
struct node *left;
struct node *right;
};
struct node *createQueue(int *front, int *rear)
{
struct node *queue = (struct node*)malloc(sizeof(struct node) * MAX_Q_SIZE);
*front = *rear = 0;
return queue;
}
void enQueue(struct node *queue, int *rear, struct node *newNode)
{
queue[*rear].data = newNode->data;
queue[*rear].left = newNode->left;
queue[*rear].right = newNode->right;
(*rear)++;
}
struct node *deQueue(struct node *queue, int *front)
{
(*front)++;
return &queue[*front - 1];
}
struct node *newNode(int data)
{
struct node *node = (struct node*)malloc(sizeof(struct node));
node->data = data;
node->left = NULL;
node->right = NULL;
return node;
}
void printBFS(struct node *root)
{
int front,rear;
struct node *queue = createQueue(&front, &rear);
struct node *tempNode = root;
while(tempNode != NULL)
{
printf("%d ",tempNode->data);
if(tempNode->left != NULL)
enQueue(queue,rear,tempNode->left);
if(tempNode->right != NULL)
enQueue(queue,rear,tempNode->right);
tempNode = deQueue(queue,front);
}
}
int main()
{
struct node *root = newNode(1);
root->left = newNode(2);
root->right = newNode(3);
root->left->left = newNode(4);
root->left->right = newNode(5);
printBFS(root);
return 0;
}
I am getting following 4 types of warnings :
BFS2.c: In function ‘printBFS’:
BFS2.c:60:13: warning: passing argument 2 of ‘enQueue’ makes pointer from integer without a cast [enabled by default]
enQueue(queue,rear,tempNode->left);
^
BFS2.c:23:6: note: expected ‘int *’ but argument is of type ‘int’
void enQueue(struct node *queue, int *rear, struct node *newNode)
^
BFS2.c:63:9: warning: passing argument 2 of ‘deQueue’ makes pointer from integer without a cast [enabled by default]
tempNode = deQueue(queue,front);
^
BFS2.c:34:14: note: expected ‘int *’ but argument is of type ‘int’
struct node *deQueue(struct node *queue, int *front)
Can anyone please help me to clarify the doubts as to why I am getting the warnings. I am unable to figure out the problems here. :(
You are passing int variables where int* (pointer to int) is expected. Pass the address of an int variable with & the address of operator. Multiple examples :
enQueue(queue, &rear, tempNode->left);
enQueue(queue, &rear, tempNode->right);
tempNode = deQueue(queue, &front);
As David has pointed out, the program will crash (segmentation fault). You may want to rethink the design of deQueue and/or what should happen if both tempNode->left and tempNode->right are NULL.
Instead of passing front and rear to enQueue() and deQueue(), pass &front and &rear. The & (address-of operator) takes the address of the variable. Since both front and rear are ints, this operator will create the correct result, an int *.
As an aside: don't cast the return value of malloc().
Your immediate pointer problems come from attempting to pass an int as a pointer:
int front,rear;
...
enQueue(queue,&rear,tempNode->left);
// enQueue(queue,rear,tempNode->left);
You have the same issue with deQueue immediately following. However, you have larger issues to deal with. Once you fix the pointer issues you will be faced with a Segmentation fault..
And to not leave you hanging, you simply need to go back and rework your queue implementation, it is a wreck. You will generate a Segmentation fault because your value for front in deQueue grows unchecked until i reaches a value of 100 and you attempt to write beyond the end of your MAX_Q_SIZE block of memory.
If you are brushing up on pointers, then don't torture pointers to try and shoehorn them into array syntax. There is no need for passing struct node *queue and then attempting to find array index syntax that will work:
queue[*rear].right = newNode->right;
when a simple pointer expression will do:
(queue + *rear)->right = newNode->right;
The same applies to:
return (queue + *front - 1); // syntax only your queue logic need fixing
This will make your code much more readable and reduce the chance for error when you pass pointers but then try and make the pointer work with something like:
return &queue[*front - 1];

checking the elements of a struct through a void pointer in C

I have an assignment about a labyrinth solving algorithm and I used a path tree to solve it, these are my structs:
typedef struct node* nodePtr;
typedef struct root{
int coordX;
int coordY;
nodePtr child[4];
} root;
typedef struct node{
int coordX;
int coordY;
char val;
nodePtr child[3];
void* parent;
} node;
The parent pointer can be either a pointer to root or a pointer to node to not to have a loop in tree. I checked this thing on assigning nodes:
void assignNode(nodePtr *nodeAddr, int x, int y, char **maze, void *parent){
...some codes...
if(y != parent->coordY && x != parent->coordX)
This is where I get annoying error of
dereferencing 'void *' pointer
error: request for member 'coordY' in something not struct or union
error: request for member 'coordX' in something not struct or union
You can't de-reference a void* like this. It needs to know the type of pointer (in your case either node* or root*). So, you need to typecast your pointer (either node* or root*). In this particular case, as node.
ie instead of
if(y != parent->coordY && x != parent->coordX)
write
if(y != ((node*)parent)->coordY && x != ((node*)parent)->coordX)
But since it your code, as you mentioned it could be either kind of the pointer (node* or root*), you need to have some way to identify it and then do the typecasting appropriately.

C implementation of skew heap

I'm trying to implement a skew heap in C, but my code doesn't compile. I'm not that experienced in C and never created any type of heap in C. That is why I don't know how to fix it, I'm hoping someone can point me the right direction. I have been reading articles about the skew heap and this is what I got so far using the algorithms I have found online. Thanks in Advance.
typedef struct node
{
int value;
struct node * root;
struct node * leftchild;
struct node * rightchild;
} Node;
struct skewHeap
{
struct node * root;
};
void skewHeapInit (struct skewHeap * sk)
{
sk->root = 0;
}
void skewHeapAdd (struct skewHeap *sk)
{
struct node *n = (struct node *) malloc(sizeof(struct node));
assert(n != 0);
n->value = 0;
n->leftchild = 0;
n->rightchild = 0;
line 185. s->root = skewHeapMerge(s->root, n);
}
void skewHeapRemoveFirst (struct skewHeap *sk)
{
struct node * n = sk->root;
free(n);
sk->root = skewHeapMerge(n->leftchild, n->rightchild);
}
line 196. struct node * skewHeapMerge(struct node *left, struct node *right)
{
struct node *temp = (struct node *) malloc(sizeof(struct node));
if (left == NULL)
return *right;
if (right == NULL)
return *left;
if (left->value < right-> value)
{
temp = left->leftchild;
left->leftchild = skewHeapMerge(left->rightchild, right);
left->rightchild = temp;
return left;
}
else
{
temp = right->rightchild;
right->rightchild = skewHeapMerge(right->leftchild, left);
right->leftchild = temp;
return right;
}
}
These are the compilations errors I'm getting at the moment:
program.c: In function ‘skewHeapAdd’:
program.c:185: warning: implicit declaration of function ‘skewHeapMerge’
program.c:185: warning: assignment makes pointer from integer without a cast
program.c: In function ‘skewHeapRemoveFirst’:
program.c:191: warning: assignment makes pointer from integer without a cast
program.c: At top level:
program.c:196: error: conflicting types for ‘skewHeapMerge’
program.c:185: note: previous implicit declaration of ‘skewHeapMerge’ was here
program.c: In function ‘skewHeapMerge’:
program.c:202: error: incompatible types when returning type ‘struct node’ but ‘struct node *’ was expected
program.c:205: error: incompatible types when returning type ‘struct node’ but ‘struct node *’ was expected
Regarding the compiler errors,
program.c: In function ‘skewHeapAdd’:
program.c:185: warning: implicit declaration of function ‘skewHeapMerge’
program.c:185: warning: assignment makes pointer from integer without a cast
tells you that no prototype of skewHeapMerge is in scope where skewHeapAdd is defined, hence (the compiler apparently operates in C89 mode, but thankfully warns about it), the compiler supposes an implicit declaration with return type int for skewHeapMerge.
Add a header file with prototypes for all your functions, and #include that in all *.c files where these functions are used or defined, so that the compiler knows the types of the functions.
program.c: In function ‘skewHeapRemoveFirst’:
program.c:191: warning: assignment makes pointer from integer without a cast
that should be the line
sk->root = skewHeapMerge(n->leftchild, n->rightchild);
where sk->root is a struct node*, but due to the implicit declaration of skewHeapMerge, that is assumed to return an int.
program.c: At top level:
program.c:196: error: conflicting types for ‘skewHeapMerge’
program.c:185: note: previous implicit declaration of ‘skewHeapMerge’ was here
here the compiler finds that the definition of skewHeapMerge gives a type conflicting with the one from the implicit declaration.
program.c: In function ‘skewHeapMerge’:
program.c:202: error: incompatible types when returning type ‘struct node’ but ‘struct node *’ was expected
program.c:205: error: incompatible types when returning type ‘struct node’ but ‘struct node *’ was expected
That is for the lines
if (left == NULL)
return *right;
if (right == NULL)
return *left;
where you ought to return right resp. left instead of *right resp. *left (I overlooked that at first).
You have a mistake in skewHeapRemoveFirst
void skewHeapRemoveFirst (struct skewHeap *sk)
{
struct node * n = sk->root;
free(n);
sk->root = skewHeapMerge(n->leftchild, n->rightchild);
}
where you use n after you freed it. You have to exchange the last two lines in that function.
And in skewHeapMerge
struct node * skewHeapMerge(struct node *left, struct node *right)
{
struct node *temp = (struct node *) malloc(sizeof(struct node));
if (left == NULL)
return *right;
if (right == NULL)
return *left;
you are leaking memory. Remove the allocation, since if temp is used at all, you assign either left->leftchild or right->rightchild to it.

Resources