使用联合结构的可扩展地图矢量

时间:2013-03-27 13:59:35

标签: c pointers vector struct

一开始我必须道歉,如果我做了第二个主题而不是坚持第一个但我不熟悉stackoverflow。

我在上一个问题中曾问过: Creating dynamic vector on predefined struct

并且收到了很多关于我所遇到的问题的可用信息。但问题对我来说仍然不太透明。

仍在工作@那个结构:

typedef struct somestruct_s {
    int s;
    union {
        unsigned char *ptr;
        unsigned char l_ptr[sizeof(char *)];
    };
}somestruct_t; 

自从我上一个问题以来,我一直在编码并尽力找到解决方案。从那以后,问题变得更加清晰。该程序的目的是创建一个动态和可扩展的映射,映射将用于位操作。端点是一个地图,我们可以在其上设置一些位:将地图的260索引设置为1.如果地图可以适合指向地图的指针占用的内存,那么我们可以将它放在那里,那就是点这个联盟。另一个问题是,如果有关于该位不适合地图的位的问题则没有错误。我们简单地回答,有0位。例如,如果我们在位置上设置0不适合该地图,我们不会扩展地图。地图扩展应仅在1种情况下进行,“我们需要在地图之外将位设置为1”。

AnatolyS给了我一些破冰技巧:

一个函数,如果我理解的话,根据大小返回指针或映射:

unsigned char* somestruct_get_bitmap(somestruct_t* ths) {
    if( sizeof(char*) > ths->s ) 
        return ths->ptr;
    return ths->l_ptr;
}

并对contructor /析构函数进行了一点澄清:

unsigned char* somestruct_init(somestruct_t* ths, unsigned char* ptr) {
    ths->s = strlen(ptr) + 1;
    if( sizeof(char*) > ths->s )  {
       ths->ptr = strdup(ptr);
       return;
    }
    strcpy(ths->l_ptr, ptr);
}

unsigned char* somestruct_destroy(somestruct_t* ths) {
    if( sizeof(char*) > ths->s )  {
        free(ths->ptr);
        return;
    }
}

但我还是觉得不够清楚。特别是我不太了解构造函数以及在扩展映射的情况下内存realloc应该是什么样子。 或者如何操纵指针来设置和获取可扩展地图的值。

很抱歉,我不能表达这么简单,但信息有限。据我所知;)

1 个答案:

答案 0 :(得分:0)

如果我理解你要做什么,你需要大量的相邻字节,任何类型的数据,你将用于位操作,并将动态地改变它的大小。

在这种情况下,它不是火箭科学。我完全不知道关于字符串的混乱和混淆的联合(它不会保存任何内存以外的东西)在哪里是有益的。指针代码的大小也没有任何意义。

仅仅做这样的事情:

#include <stdint.h>
#include <stdbool.h>

typedef struct
{
  uint8_t* data;
  size_t   size;
} bitmap_t;


bool bitmap_create (bitmap_t* bm, size_t size)
{
  bm->size = size;
  bm->data = malloc(size);
  return bm->data != NULL;  // return false if allocation failed, otherwise true
}

void bitmap_delete (bitmap_t* bm)
{
  free(bm->data);
}

bool bitmap_resize (bitmap_t* bm, size_t new_size)
{
  bm->size = new_size;
  bm->data = realloc(new_size);
  return bm->data != NULL;
}

void bitmap_set_bit (bitmap_t* bm, size_t byte_n, uint8_t bit_n)
{
  if(byte_n >= bm->size || bit_n > 7)
  {
    halt_and_catch_fire();
  }

  bm->data[byte_n] |= 1u << bit_n;
}

void bitmap_clear_bit (bitmap_t* bm, size_t byte_n, uint8_t bit_n)
{
  if(byte_n >= bm->size || bit_n > 7)
  {
    halt_and_catch_fire();
  }

  bm->data[byte_n] &= ~(1u << bit_n);
}