简体   繁体   English

我们可以在C中的main函数中定义函数原型吗?

[英]Can we define function prototype in main function in C?

in my university our teacher taught us "we define function prototype before main function. Like: 在我的大学,我们的老师教我们“我们在主要功能之前定义功能原型。喜欢:

#include<stdio.h>
void findmax(float, float);
int main()
{
    //code goes here
}

But today my friend showed me they learned they put prototype inside main function. 但是今天我的朋友告诉我他们学会了将原型放在主要功能中。 Like: 喜欢:

#include<stdio.h>
int main()
{
    void findmax(float, float);

    float firstnum, secondnum;

    printf("Enter first:");
    scanf("%f", &firstnum);

    printf("Enter second:");
    scanf("%f", &secondnum);

    findmax(firstnum, secondnum);
}

void findmax(float x, float y)
{
    float maxnum;

    if(x>y)
    {
            maxnum=x;
    }

    else
    {
       maxnum=y;
    }

    printf("The max is %f", maxnum);
}

They both works.I wonder if there are differences between them. 它们都有效。我想知道它们之间是否存在差异。 Thanks. 谢谢。

Can we define function prototype in main function in C? 我们可以在C中的main函数中定义函数原型吗?

Yes. 是。

I wonder if there are differences between them 我想知道他们之间是否存在差异

The difference is that in first snippet prototype is global while in second it is local to main . 不同之处在于,第一个片段原型是全局的,而在第二个片段中,它是本地的main原型。 findmax will be visible after its declaration and/or definition. findmax将在声明和/或定义后显示。

#include<stdio.h>
void foo();
int main()
{
    void findmax(float, float); 
    foo();
    findmax(10, 20);  // It knows findmax by the prototype declared above
}

void findmax(float x, float y)
{
    float maxnum;

    if(x>y)
        maxnum=x;
    else
        maxnum=y;

    printf("The max is %f", maxnum);
}

void foo(){   // foo is using findmax after its definition.
    findmax(12, 30);
}

If you declare the function in main() it is scoped in the main() and you cannot access it in another function. 如果在main()中声明该函数,则它在main()中作用域,并且您无法在另一个函数中访问它。 But if you declare it at the start of the file or in a header file you can use it in any function. 但是如果你在文件的开头或头文件中声明它,你可以在任何函数中使用它。

If foo is declared in outside a function, it can be called from any function in the same file: 如果在函数外部声明了foo ,则可以从同一文件中的任何函数调用它:

void foo(); // <-- global declaration

int main() {
  foo();    // <-- works, foo() is declared globally
}

void otherfunc() {
  foo();    // <-- works, foo() is declared globally
}

However, if foo is declared inside a function, it can only be used within the same scope: 但是,如果foo在函数内声明,则它只能在同一范围内使用:

int main() {
  void foo(); // <-- scoped declaration
  foo();      // works, foo() is declared in same scope
}

void otherfunc() {
  foo();      // ERROR: foo() is not declared in scope of otherfunc()
}

In either case, foo must be declared before it is used. 在任何一种情况下,必须在使用之前声明foo

A straightforward answer to your question would simply be a YES. 对你的问题直截了当的答案就是肯定的。 But when it comes to the scope, I'd like to add more. 但是当谈到范围时,我想补充更多。

What others suggest is right -- if you declare a function inside another function, the first one's scope is usually limited to the second one. 其他人的建议是对的 - 如果你在另一个函数中声明一个函数,第一个函数的范围通常限于第二个函数。 For the example you provided, it is perfectly safe to say so. 对于您提供的示例,这样说是完全安全的。 But that may not be the case always. 但总有可能并非如此。 Consider the following code: 请考虑以下代码:

#include <stdio.h>

/* Can be accessed from anywhere in this file
 * because defined before anything else.
 */
void print_hello() {
        puts("Hello!");
}

int main() {
        void print_hello(); /* Not needed actually */
        void print_namaste();
        void print_hi();

        print_namaste();
        print_hi();
}

/* The following two functions cannot be
 * accessed from within the above two functions
 * unless these two are declared inside them
 * or at the starting of this file
 */
void print_namaste() {
        puts("Namaste!");
        print_hello();
}

void print_hi() {
        puts("Hi!");
}

Here you can see that print_hello() is declared inside main() . 在这里你可以看到print_hello()main()声明。 But that is redundant. 但这是多余的。 print_hello() has already been introduced into the compiler. print_hello()已经引入编译器。 There is no need of declaration to use it inside this file (if you use it inside other files and compile them independently, then you'll have to declare it inside those files or write a header file to do so). 没有必要声明在这个文件中使用它(如果你在其他文件中使用它并独立编译它们,那么你必须在这些文件中声明它或写一个头文件来这样做)。 What my point is, declaring print_hello() inside main() has not rendered it local, at least in this example . 我的观点是, main()声明print_hello()并没有将它呈现为本地,至少在本例中 You can see print_namaste() calling it successfully without any additional declaration. 您可以看到print_namaste()成功调用它而无需任何其他声明。

But that is not the case with print_namaste() and print_hi() . 但是print_namaste()print_hi()不是这种情况。 They require declaration to be used from within main() because they are introduced to the compiler only after main() has been defined. 它们需要在main()使用声明,因为只有在定义了main()之后才会将它们引入编译器。

print_namaste() will only be visible to the functions inside which we declare it, and to those functions which are defined after print_namaste() . print_namaste()只对我们声明它的函数以及print_namaste()之后定义的函数print_namaste() In this example, print_namaste() is not visible to print_hello() (unless declared inside it or before it), but visible to main() because declared inside it, and visible to print_hi because its definition comes only after the definition of print_namaste() . 在这个例子中, print_namaste()是不可见的print_hello()除非它里面或之前申报),但可见main()因为它里面声明的,可见print_hi ,因为它的定义只定义之后来到print_namaste()

In VC2008 the following is valid: 在VC2008中,以下内容有效:

int main(void)
{
    void foo(void);
    //...
}
void test(void)
{
    foo();
}

My believe was that prototype declarations are valid anywhere and their scope is at least from the point of declaration to the end of file. 我相信原型声明在任何地方都有效,它们的范围至少从声明点到文件末尾。

Looking at the C99 standard: 看看C99标准:

6.2.1 Scope of Identifiers 6.2.1标识符的范围

An identifier can denote an object; 标识符可以表示对象; a function; 功能; a tag or a member of a structure, union, or enumeration; 标签或结构,联合或枚举的成员; a typedef name; 一个typedef名称; a label name; 标签名称; a macro name; 一个宏名; or a macro parameter... For each different entity that an identifier designates, the identifier is visible (ie, can be used) only within a region of program text called its scope... identifier has scope determined by the placement of its declaration (in a declarator or type specifier). 或宏参数...对于标识符指定的每个不同实体,标识符仅在称为其范围的程序文本区域内可见(即,可以使用)...标识符的范围由其声明的放置确定(在声明者或类型说明符中)。 If the declarator or type specifier that declares the identifier appears outside of any block or list of parameters, the identifier has file scope, which terminates at the end of the translation unit. 如果声明标识符的声明符或类型说明符出现在任何块或参数列表之外,则标识符具有文件范围,该范围终止于转换单元的末尾。 If the declarator or type specifier that declares the identifier appears inside a block or within the list of parameter declarations in a function definition, the identifier has block scope, which terminates at the end of the associated block. 如果声明标识符的声明符或类型说明符出现在块内或函数定义中的参数声明列表中,则标识符具有块作用域,该作用域终止于关联块的末尾。

This would mean that VC2008 is wrong. 这意味着VC2008是错误的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM