简体   繁体   中英

different implementations for the same function (c/c++)

is it possible to have 2 (or more) different implementations for the same function declared in a header file? I'll give an example - let's say we have a header file called common.h and 2 source files called src1.c and src2.c .

common.h

//lots of common function declarations implemented in some file common.c 
int func(int a, int b);

src1.c

#include "common.h"

int func(int a, int b)
{
    return a+b;
}

src2.c

#include "common.h"

int func(int a, int b)
{
    return a*b;
}

let's say that I want each of the source file to use its local version of func() . is it possible to do so?

Yes, but if you attempted to link your main program against both src1 and src2 you would encounter an error because it wouldn't know which definition to use.
Headers are just ways for other code objects to be aware of what's available in other objects. Think of headers as a contract. Contracts are expected to be filled exactly one time, not zero or multiple times. If you link against both src1 and src2 , you've essentially filled the int func(int a, int b); contract twice.

If you need to alternate between two functions with the same signature, you can use function pointers .

If you want each source file to only use its local implementation of func , and no other module uses those functions, you can remove the declaration from the header and declare them as static .

src1.c

static int func(int a, int b)
{
    return a+b;
}

src2.c

static int func(int a, int b)
{
    return a*b;
}

By doing this, each of these functions is only visible in the module it is defined in.

EDIT:

If you want two or more functions to implement an interface, you need to give them different names but you can use a function pointer to choose the one you want.

common.h

typedef int (*ftype)(int, int);
int func_add(int a, int b);
int func_mult(int a, int b);

src1.c

#include "common.h"

int func_add(int a, int b)
{
    return a+b;
}

src2.c

#include "common.h"

int func_mult(int a, int b)
{
    return a*b;
}

Then you can chose one or the other:

ftype func;
if (op=='+') {
    func = func_add;
} else if (op=='*') {
    func = func_mult;
...
}

int result = func(value1,value2);

如果你用每个src [x] .c编译它,你就可以在.c的任何函数中使用它

You can decide to not expose the function implementation to other translation units. In c, use keyword static before the function signature right where you implement the function (see code below); In C++, you can also use unnamed namespaces. By doing so, the linker will not give you an error, and each translation unit will use it's own implementation:

Suppose the following two translation units main.c and another.c . Both have their (private) implementation of int function(a,b) , such that they yield different results when calling it:

extern void someOtherFeature();

static int function (a,b) {
    return a+b;
}

int main(){

    int x = function(1,2);
    printf("main: function(1,2)=%d\n", x);
    someOtherFeature();
}

// another.c:
#include <stdio.h>

static int function (a,b) {
    return a*b;
}

void someOtherFeature() {
    int x = function(1,2);
    printf("someOtherFeature: function(1,2)=%d\n", x);
}

Output:

main: function(1,2)=3
someOtherFeature: function(1,2)=2

However, if both translation units exposed their implementations (ie both omitted keyword static , then the linker would report an error like duplicate symbol _function in:... .

If you want each source file to use a local version of func , just put it in an unnamed namespace:

For example src1.C :

namespace
{
    int func(int a, int b)
    {
        return a+b;
    }
}

Then each source file will use its own version. You don't need to declare it in the header.

Note that your original code with the definitions at global namespace and declared in the header violates the one definition rule (two function definitions for the same name must always have the same definition), invoking undefined behavior, no diagnostic required.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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