数组的extern声明

时间:2017-12-27 23:39:25

标签: c99 extern variable-declaration

我有一个在源文件中定义的编译时确定大小的数组。

euro.cross[as.matrix(myDF)]
# [1]  1.204921087 18.305448539  0.003070713  0.010992059  0.057234508

将来可能会更改元素的数量,因此我不想在括号中对其进行硬编码。

需要从多个源文件访问此数组,因此我尝试在标头中向其添加extern声明。但是由于隐式数组大小,我不确定这是否可行。我尝试了两种变体:

const int array[] = {1, 3, 3, 7};

是否可以这样做或者我应该寻找解决方法吗?

1 个答案:

答案 0 :(得分:1)

在声明变量的标题中,写:

[ResponseType(typeof(FacebookDataUser))]
        public async Task<IHttpActionResult> PostFacebookDataUser(FacebookDataUser facebookDataUser)
        {
            if (!ModelState.IsValid)
            {
                return BadRequest(ModelState);
            }

            FacebookDataUser faceUser = await db.FacebookDataUsers.FindAsync(facebookDataUser.FacebookDataUserId);

            if (faceUser == null)
            {
                facebookDataUser.DateOfInsert = DateTime.Now;
                db.FacebookDataUsers.Add(facebookDataUser);

            }

            else
            {
                var listEvents = facebookDataUser.FaceEvents.FaceEventDatas.ToList();

                for (var i=0; i<= facebookDataUser.FaceEvents.FaceEventDatas.Count; i++)
                {
                    var eventName = listEvents[i].name;

                    var events = db.FacebookDataUsers.Where(b => b.FaceEvents.FaceEventDatas.Select(x => x.name).ToList().Contains(eventName)).FirstOrDefault();
                    if (events == null)
                    {
                        FaceEventData faceEventsData = listEvents[i];

                        try
                        {
                            faceUser.FaceEvents.FaceEventDatas.Add(faceEventsData);

                        }
                        catch (Exception e)
                        {

                        }
                    }
                }

                db.FacebookDataUsers.Add(faceUser);


            }

            await db.SaveChangesAsync();

        }

你是对的,其他文件不知道数组的大小。那太棘手了。您可以在标题中使用:

extern const int array[];

并且定义了数组:

extern const int array[];
extern const size_t array_size;

您需要包含定义数组的标题,以确保交叉引用是正确的。如果您选择使用const int array[] = {1, 3, 3, 7}; const size_t array_size = sizeof(array) / sizeof(array[0]); 而不是int,我将不会向您提出任何投诉(但如果您将编译器设置得足够繁琐,则可能对该主题有不同的看法。)

请注意,数组大小不是标准含义内的“整数常量”;例如,它不能用于size_t标签。如果使用case声明另一个数组,它将是一个VLA - 可变长度数组。此类数组不能在文件范围内声明(或在函数内部使用array_size存储类)。

另见How do I use extern to share variables between source files?

插图

答案的MCVE(Minimal, Complete, Verifiable Example):

<强> static

ext-def.h

<强> #include <stddef.h> extern const int array[]; extern const size_t array_size;

ext-def.c

<强> #include "ext-def.h" const int array[] = {1, 3, 3, 7}; const size_t array_size = sizeof(array) / sizeof(array[0]);

ext-use.c

<强>汇编

在运行macOS High Sierra 10.13.2的MacBook Pro上使用GCC 7.2.0,使用martinkunevcomment指定的选项:

#include "ext-def.h"
#include <stdio.h>

int main(void)
{
    for (size_t i = 0; i < array_size; i++)
        printf("%zu: %d\n", i, array[i]);
    return 0;
}

使用我的默认编译选项(C11而不是C99):

$ gcc -std=c99 -pthread -O2 -fstrict-aliasing -fomit-frame-pointer -pedantic -o ext-def ext-def.c ext-use.c
$ ./ext-def
0: 1
1: 3
2: 3
3: 7
$

在任何一组选项下均可免于警告。您可以将$ gcc -O3 -g -std=c11 -Wall -Wextra -Werror -Wmissing-prototypes -Wstrict-prototypes -c ext-def.c $ gcc -O3 -g -std=c11 -Wall -Wextra -Werror -Wmissing-prototypes -Wstrict-prototypes -c ext-use.c $ 添加到C11命令行,而不会收到任何警告。