How does a forward declaration work?

I understand that declaring a factorial before main. But how can you calculate the answer when the factorial comes after it?

#include <stdio.h>

long long factorial(int);

int main()
{
    int n;
    long long f;

    printf("Enter a number and I will return you its factorial:\n");
    scanf_s("%d", &n);

    if (n < 0)
        printf("No negative numbers allowed!\n"); //prevent negative numbers
    else
    {
        f = factorial(n);
        printf("The factorial of %d is %ld\n", n, f);
    }

    return 0;
}

long long factorial(int n)
{
    if (n == 0)
        return 1;
    else
        return (n * factorial(n - 1));
}

      

+3


source to share


4 answers


But how is the main counting of the answer when the factorial comes after it?

First, it main

doesn't compute the answer; it is your function factorial

that does it for you. There are also 3 steps that I think you need to know when writing programs:

  • You write code in a file.
  • You compile the file, and the compiler checks for syntax errors, at this stage the computation of the code does not just happen as simple lexical analysis.
  • Then the connection happens later. If you get a linker error, it means that your code compiles fine, but some function or library that is not needed cannot be found. This happens in what we call the linking step and will prevent the executable from being created. Many compilers perform both a compilation and a linking step.

Then when you actually run your code, then when the control flow of the code goes into the function factorial

, when the calculation happens, that is, at runtime. Use Debugger to see this.

Below image is taken from Compiling, Linking and Building C / C ++ Applications



enter image description here

From the Wiki :

In computer programming, a forward declaration is an identifier declaration (denoting an object such as a type, variable, constant, or function) for which the programmer has not yet fully defined .... This is especially useful for single-pass compilers and separate collections. Forward declaration is used in languages ​​requiring a declaration before use; it is necessary for mutual recursion in such languages, since it is impossible to define such functions (or data structures) without direct reference in one definition: one of the functions (respectively data structures) must be defined first. it is also useful for flexible code organization, for example if one wants to put the main body at the top and name the functions below it.

So basically the function main

does n't need to know how it works at all factorial

.

+4


source


It works like this: let's take an example to find factorial 3

Recursion:

enter image description here



Since the factorial 0

is 1 and the factorial is 1

also 1, you can write as

if(n <= 1)
     return 1;

      

+1


source


But how is the main counting of the answer when the factorial comes after it?

The order in which a C program runs is determined in part by the order in which the text appears.

For example, take a look at the function printf

you are using. It doesn't show up at all in your program; it is in the library that is associated with your program.

As a result of direct declaration (from this point in the translation block), it is assumed that there is such and such a function that has a specific name, arguments and return value.

The simple answer is that your C program is processed from start to finish before it starts executing. Thus, by the time it appeared, the main

function factorial

had already been noticed and processed by the C compiler.

A compiled function is assigned to an factorial

address, and this address is "accessed" by the compiled function main

when the program is linked.

The reasons why a forward declaration is required is because C is an old-fashioned language, originally designed for one-pass compilation. This means that the compiler is "translated as it goes": functions earlier in the compiler are compiled and published before later functions are visible. In order to properly compile a function call that appears later (or tends to appear elsewhere, such as in a different translation unit), some information about that function must be declared in order for it to be known at that point.

+1


source


Since in the main function, when the compiler sees this function f = factorial(n);

, the compiler has no idea what it means. it doesn't know where the function is defined, but it knows the argument that the function receives is correct because it is a user-defined function that has definition

after the main function.

Hence, there must be some way to tell the compiler that I am using a named function factorial

that returns a long long

single argument int

; so you define prototype

functions before main()

.

Whenever you call a function factorial

, the compiler cross-checks the function prototype

and ensures that the function is called correctly.

The function protocol is not required if you define the function before the main one.

An example of a case where prototyping is not required:

/*function prototyping is not required*/
long long factorial(int n)
{
 //body of factorial
}

int main()
{
 ...
 f=factorial(n);
 ... 
}

      

The compiler knows the definition here factorial

; it knows the return type, the argument type and the function name, and also before it gets called in the main.

+1


source







All Articles