C 存储在某个函数静态变量中的函数共享的内存

C 存储在某个函数静态变量中的函数共享的内存,c,static,C,Static,在一个更大的项目中,我将编写一个在同一内存结构上工作的C函数列表。 由于这些函数在代码的不同部分(以及在单独编译然后链接的不同库中)被调用,因此我希望避免将指向内存结构的指针作为参数传递给每个函数调用 我在考虑将内存结构作为静态变量存储在单个函数中,并始终在其他函数中调用该函数以获取指向内存结构的指针。 在下面的示例中,我使用storage()设置sto指针 我测试了下面的代码,它似乎工作得很好。这是标准方法吗?我在冒什么风险?这会一直有效吗?更好的解决方案 没有对我的函数的并发调用。当然,我也

在一个更大的项目中,我将编写一个在同一内存结构上工作的C函数列表。 由于这些函数在代码的不同部分(以及在单独编译然后链接的不同库中)被调用,因此我希望避免将指向内存结构的指针作为参数传递给每个函数调用

我在考虑将内存结构作为静态变量存储在单个函数中,并始终在其他函数中调用该函数以获取指向内存结构的指针。 在下面的示例中,我使用
storage()
设置
sto
指针

我测试了下面的代码,它似乎工作得很好。这是标准方法吗?我在冒什么风险?这会一直有效吗?更好的解决方案

没有对我的函数的并发调用。当然,我也可以释放分配的内存

#include <stdio.h>
#include <stdlib.h>

int* storage(int get_set)
{
    static int* sto;
    if (get_set==1)
    {
        sto=malloc(2*sizeof(int));
        sto[0]=1;
        sto[1]=2;
    }
    printf("storage: content = %d %d, pointer= %d\n", sto[0], sto[1], sto);
    return sto;
}

void add11()
{
    int* sto =storage(0);
    sto[0]+=1;
    sto[1]+=1;
    printf("add11: content = %d %d, pointer= %d \n", sto[0], sto[1], sto);
}

void multo0()
{
    int* sto =storage(0);
    sto[0]=sto[1]*sto[0];
    sto[1]=0;
    printf("multo0: content = %d %d, pointer= %d\n", sto[0], sto[1], sto);
}


int main(void) {
    storage(1); // initialize memory only once
    add11();  // work on memory 
    multo0();
    add11();
    // ...
    return 0;
}
#包括
#包括
int*存储(int get_set)
{
静态int*sto;
if(get_set==1)
{
sto=malloc(2*sizeof(int));
sto[0]=1;
sto[1]=2;
}
printf(“存储:内容=%d%d,指针=%d\n”,sto[0],sto[1],sto”);
返回sto;
}
void add11()
{
int*sto=storage(0);
sto[0]+=1;
sto[1]+=1;
printf(“add11:content=%d%d,指针=%d\n”,sto[0],sto[1],sto”);
}
void multo0()
{
int*sto=storage(0);
sto[0]=sto[1]*sto[0];
sto[1]=0;
printf(“multo0:content=%d%d,指针=%d\n”,sto[0],sto[1],sto);
}
内部主(空){
存储器(1);//仅初始化内存一次
add11();//在内存上工作
multo0();
add11();
// ...
返回0;
}
我想要这样的东西的原因如下:

我正在编写的函数集执行单独的、辅助的可选图像增强任务,并以不同的方式从以前观察到的图像中学习<代码>sto存储此学习和参数化选项的内存

在整个项目中,我的函数将在多个嵌套函数调用中调用。将
sto
作为参数传递意味着在项目的主体中声明一个指针,并将大量与我的函数执行的任务无关的核心嵌套函数更改为传递附加参数

此外,同一组功能将集成到多个稍有不同的项目中,因此,集成的侵入性较小,需要尽可能少地修改外部代码,这将是一个优势

对于可读性问题,所有且仅访问共享内存的函数具有相同的前缀。我知道这不是一个完整的解决方案,但我相信它增加了一点可读性


除了更改所有函数以在整个项目中执行
sto
之外,是否仍然没有其他选择?

这肯定不是标准做法,并且会增加代码的可读性问题。想象一下,刚刚添加到项目中的某个人现在需要使用此代码,他/她会非常困惑。此外,每个函数调用都可能会导致一些开销,因此最好传递一个指向所有函数的指针。

这肯定不是标准做法,并且会给代码增加一定程度的可读性问题。想象一下,刚刚添加到项目中的某个人现在需要使用此代码,他/她会非常困惑。此外,每个函数调用都可能会导致一些开销,因此最好传递一个指向所有函数的指针。

这有几个缺点

首先,您的函数每次调用时都会分配内存,但从函数名中不清楚调用方是否需要显式释放返回的内存

其次,它作为一个全局值,最好使用指针在函数之间传递数据,因为从可读性的角度来看,它更清楚地表明哪个函数只需查看函数原型即可访问数据:

void foo(storage* p);
void foo1();
void foo2(const storage* p);
第三,访问数据时会增加开销

您的存储函数中也存在内存泄漏,您将sto声明为静态,但在将其分配给malloc之前,不检查它是否已经指向某个对象

static int* sto;
if (get_set==1)
{
    sto=malloc(2*sizeof(int));
    sto[0]=1;
    sto[1]=2;
}
应该是

static int* sto;
if (get_set==1)
{
    if ( sto != NULL ) 
    {
      free(sto);
    }
    sto=malloc(2*sizeof(int));
    sto[0]=1;
    sto[1]=2;
}
如果仍然坚持使用此方法,则至少应该将值放入结构中,然后复制这些值,并且不需要每次都分配堆(缺点是会增加一些开销)


这有几个缺点

首先,您的函数每次调用时都会分配内存,但从函数名中不清楚调用方是否需要显式释放返回的内存

其次,它作为一个全局值,最好使用指针在函数之间传递数据,因为从可读性的角度来看,它更清楚地表明哪个函数只需查看函数原型即可访问数据:

void foo(storage* p);
void foo1();
void foo2(const storage* p);
第三,访问数据时会增加开销

您的存储函数中也存在内存泄漏,您将sto声明为静态,但在将其分配给malloc之前,不检查它是否已经指向某个对象

static int* sto;
if (get_set==1)
{
    sto=malloc(2*sizeof(int));
    sto[0]=1;
    sto[1]=2;
}
应该是

static int* sto;
if (get_set==1)
{
    if ( sto != NULL ) 
    {
      free(sto);
    }
    sto=malloc(2*sizeof(int));
    sto[0]=1;
    sto[1]=2;
}
如果仍然坚持使用此方法,则至少应该将值放入结构中,然后复制这些值,并且不需要每次都分配堆(缺点是会增加一些开销)


由于您已经有多个要链接在一起的模块,“更标准”的方法是使用静态(对单个模块专用)变量(第一种方法),如果您需要访问器函数,请返回指向该变量的指针。但是,如果访问器只是返回指向它的指针,那么您可以简单地使用“extern”并以自然的方式访问数据(第二种方法)

第一种方法:

包含数据的模块:

使用数据的模块:

第二种方法:

包含数据的模块:

int mydata; /* note: no "static" */
extern int mydata; /* note: "extern" */

int main() {
    int* foo = &mydata;
}