【发布时间】:2014-01-16 18:07:56
【问题描述】:
我经历了以下线程:
可能我的问题是相关的。但是,虽然他们提供了在使用函数之前应该声明函数原型的解决方案,但我想探索当函数名称不匹配时会发生什么。在我的测试中,它仍然可以正常工作。
主 C 文件
#include "node.h"
int main(){
nd *head=NULL;
nd *tail=NULL;
create_node(&head, &tail, 10);
create_node(&head, &tail, 20);
create_node(&head, &tail, 15);
create_node(&head, &tail, 35);
create_node(&head, &tail, 5);
create_node(&head, &tail, 25);
print_list(head, tail);
create_node(&head, &tail, 55);
create_node(&head, &tail, 52);
create_node(&head, &tail, 125);
printf("%d\n",tail->data);
printf("%d\n",head->data);
print_list(head, tail);
return 0;
}
node.h 文件
#ifndef NODE_H
#define NODE_H
#include<stdio.h>
#include<stdlib.h>
typedef struct node{
int data;
struct node *next;
struct node *prev;
}nd;
void insert_node(nd **head, nd **tail, int data);
void print_list(nd *head, nd *tail);
#endif
node.c文件
#include "node.h"
void create_node(nd **head, nd **tail, int d){
nd *temp=(nd *) malloc(sizeof(nd));
temp->data=d;
temp->next=NULL;
temp->prev=NULL;
/* Start of the Queue. */
if(*head==NULL && *tail==NULL){
*head=temp;
*tail=temp;
}
/* Linking with tail of the Queue. */
else if((*tail)->next==NULL){
(*tail)->next=temp;
temp->prev=*tail;
*head=temp;
}
/* Adding remaining elements of the Queue. */
else{
(*head)->next=temp;
temp->prev=*head;
*head=temp;
}
}
void print_list(nd *head, nd *tail){
if(NULL==head){
printf("Queue is empty\n");
}
else{
printf("Printing the list\n");
nd *temp;
for(temp=tail;temp!=NULL;temp=temp->next){
printf("%d ",temp->data);
}
printf("\n");
}
}
输出
Printing the list
10 20 15 35 5 25
10
125
Printing the list
10 20 15 35 5 25 55 52 125
在node.h 中声明的函数的名称是insert_node,而在node.c 中它是create_node。有人可以分享一些关于它为什么运行的见解吗?但它会引发警告:
警告:函数的隐式声明
【问题讨论】:
-
之所以有效,是因为
main调用create_node并且create_node是node.c中实际声明的内容。参数类型恰好足够通用,以至于它们都可以。标头中的名称错误会导致警告。如果node.c中的create_node实际上被称为insert_node,则链接将失败并说它找不到定义为create_node的函数。 -
您的问题是“为什么我的编译器不将警告视为错误?”有一个标志。
-
这不是“工作正常”。如果调用未声明的函数会产生一些输出,那么无论如何它都是错误的(因为那时行为是未定义的)。不过,它可以假装“工作正常”。这并不意味着它确实可以正常工作。
-
如果使用 gcc,请将
-Wall -Wextra -Werror添加到 CFLAGS -
@H2CO3 接受的答案解释说,对于这种情况,带有参数的默认编译器行为是可以的。虽然隐式声明可能并不总是正确的,但在这种情况下,它看起来不仅仅是“假装工作正常”;编译器所做的假设对于 this 案例是正确的,因此 this 案例可以正常工作。
标签: c function warnings implicit-declaration