C语言中具有二维数组的结构

C语言中具有二维数组的结构,c,pointers,struct,C,Pointers,Struct,我还不太擅长C,所以我有一些问题 我有以下两个结构: typedef struct line_elems line; typedef struct cache_handler *cache; struct line_elems { // we don't care about valid/block bits in our simulator int tag; int freq; // for LRU principle }; struct cache_handler { int

我还不太擅长C,所以我有一些问题

我有以下两个结构:

typedef struct line_elems line;
typedef struct cache_handler *cache;

struct line_elems { // we don't care about valid/block bits in our simulator
  int tag;
  int freq; // for LRU principle
};

struct cache_handler {
  int hit;
  int miss;
  int evict;
  line **lines; // 2d array for sets
};
在缓存中,通过以下方式初始化:

cache make_cache(int s, int E) {
  int i;
  cache new = malloc(sizeof(struct cache_handler));
  new->hit = 0;
  new->miss = 0;
  new->evict = 0;
  line **new_line = malloc((1 << s) * sizeof(*new_line));
  for(i = 0; i < (1 << s); i++)
    new_line[i] = malloc(E * sizeof(struct line_elems));

  new->lines = new_line;
  return new;
}
现在,我想创建一个系统来搜索二维数组中的一行:

int search_lines(line *lines, int E, int tag, int frequency) {
  int i;
  for(i = 0; i < E; i++) {
    //continue here
  }
}
我有点困惑,到底应该在搜索行函数中输入什么。 如果我输入:search\u linescache->lines[0],E=5,tag=5,frequency=5,它会达到我的期望吗?也就是说,它会在我的2d数组中搜索一行吗?我觉得缓存->行[0]与行*不同。 缓存->行与缓存->行[0]之间有什么区别?这让我很困惑,因为->操作符是否隐式执行一级解引用

谢谢。

操作符不是解引用行,而是解引用缓存。这是必要的,因为缓存也是通过调用malloc创建的指针。因此,在访问它的任何字段之前,必须取消对它的引用

缓存->行是一行**

缓存->行[0]是一行*

缓存->行和缓存->行[0]有什么区别

缓存->行是结构行元素**,它是您的二维数组。实际上,它是指向2D数组的第一个元素的指针。运算符->之所以使用,是因为cache是cache\u处理程序*=您正在使用它访问struct cache\u处理程序的成员

cache->lines[0]是struct line_elems*,它是索引0处的1D数组=它也是指向2D数组的第一个元素的指针

请注意,释放此内存的顺序应与分配的顺序相反:

line **new_line = malloc((1 << s) * sizeof(*new_line));
for(i = 0; i < (1 << s); i++)
    new_line[i] = malloc(E * sizeof(struct line_elems));

是的,缓存->行[0]的引用确实返回了一个指向分配的“行”数组的指针,因此,是的,您的示例调用实际上是正确的方法

请记住,缓存->行是第二次调用malloc时分配的指针数组。它只为2^s*指针的大小分配足够的空间

下面的其余malloc为线的E*size\u分配了足够的空间

因此,当您使用->取消对缓存指针的引用,然后使用[0]取消对行指针的引用时,您将得到一个指向E行的内存指针


然后,在函数中,可以使用第[0]行到达第一行,第[E-1]行到达根据[]运算符传递到缓存->行数据指针的任何行指针数组的最后一行。

请不要将缓存称为“新建”。这是C++中的一个关键词,如果你尝试在C++中编译你的代码,它将引入一个痛苦的世界。新的是一个可怕的变量名,你应该总是使用描述性的名字,但是在C编程时,你的代码要改变为C++,这是一个可怕的推理。如果你关心编译你的代码,我会假设你会使用C++。好吧,不知道,我的代码中会改变这个。谢谢,现在,如果我真的在这行中搜索,我会放一些类似于行[I].tag=1234的东西吗?想访问每行中的特定字段吗?对不起,最后一个问题,我正在尝试创建一个“free”函数,我基本上有以下行释放我的缓存:freenew_cache->lines[I][j];但是,当我尝试这个方法时,它不起作用。注意,i,j在嵌套的for循环中。非常感谢,这真的很有帮助。我想我已经掌握了指针的窍门:
for(i = 0; i < (1 << s); i++)
    free(new_line[i]);
free(new_line);