【问题标题】:Automated Function Pointers in CC 中的自动函数指针
【发布时间】:2019-11-12 05:18:02
【问题描述】:

我在 C 中有这个问题。假设我有一个这样的结构:

struct Writer {
    char buffer[10];
    void (*writeFunction)(uint8_t*, size_t);
}

这个结构的方法使用用户给定的编写器函数指针来转储值,如下所示:

struct Writer writer;
FILE* file = fopen("test.txt", "wb");
void writeToFile(uint8_t* content, size_t size)
{
    fwrite(content, 1, size, file);
}
write.writeFunction = writeToFile;

当用户编写写入函数并手动传递它们时,这很好用。然而,有没有办法自动化这个,所以我可以说,对于每个新的 Writer 结构,都会生成一个带有 from-user-given-filepath 的新 writeFunction 指针。我试过了,但我一直在使用 C++ lambda 函数或需要来自 C++ 的 this 指针。

预期是这样的:

void generate(struct Writer* writer, const char* filename)
{
    // somehow, writer->writerfunction needs to point to a 
writeToFile function like above 
}

谢谢。

【问题讨论】:

  • 你愿意改变你打电话给writeFunction的方式来实现你的目标吗?如果你是,看看:stackoverflow.com/q/17052443/315052
  • 不,这在标准 C 中是不可能的,句号。
  • 我真的很想在 writeFunction 指针中没有额外的参数。 (我想我们总是可以将其更改为 void (writeFunction)(uint8_t, size_t, void*),其中 void" 可以重新解释为 FILE* 或不使用。我真的希望我们可以避免“完全不用”的情况,只需要必要的参数,即大小和内容)。
  • @AKJ:还有另一个相关的参数:写入的目的地本身。

标签: c pointers function-pointers


【解决方案1】:

为什么不将FILE * 存储为writer 结构的成员并将其传递给writer 函数?

struct Writer {
    char buffer[10];
    FILE *file;
    void (*writeFunction)(FILE *, uint8_t*, size_t);
}

void writeToFile(FILE *file, uint8_t* content, size_t size)
{
    fwrite(content, 1, size, file);
}

而生成函数就变成了。

void generate(struct Writer* writer, const char* filename)
{
   FILE* file = fopen(filename, "wb");
   writer->writeFunction = writeToFile;
   writer->file = file;
}

使用函数指针调用函数时,

   (*writer->writeFunction)(writer->file, writer->buffer, somesize);

【讨论】:

  • 感谢您的回答,但您不能更改 writeFunction 指针,因为它也不能写入 FILE,例如,它可以简单地通过 HTTP 发送内容。
  • @AKJ:见:dynamic dispatch
  • @jxh 感谢您的链接。
【解决方案2】:

这在标准 c 中是不可能的。

最接近封装的方法可能是将 writer struct 完全变成一个函数,唉。

void Writer(char buffer[10], void (*writeFunction)(uint8_t*, size_t));

现在您可以根据需要添加重载和/或检查writeFunction 是否为零。

【讨论】:

    猜你喜欢
    • 2021-09-21
    • 1970-01-01
    • 1970-01-01
    • 2020-06-28
    • 2016-06-23
    • 2010-11-19
    • 2021-10-30
    相关资源
    最近更新 更多