c++Map到无符号字符数组

r9f1avp5  于 2023-03-14  发布在  其他
关注(0)|答案(3)|浏览(126)

我尝试从www.example.com API中提取天气图标openweathermap.org,并使用u8 g2库(Arduino IDE,C++11)在ESP 32驱动的OLED显示器上显示它们。
在openweathermap.org天气API中,16种天气类型被定义为const *char[],例如"01d""01n""02d"等。
u8 g2库使用unsigned char数组来定义XBM位图格式的图标。我定义了所有的图标,如下所示:

static unsigned char icon01d[] = {
   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
   ...
}

图标可以通过以下方式显示在OLED上:

u8g2.drawXBMP( 96, 0, 32, 32, icon01d );

我想使用一个std::map将字符串从天气API链接到指向图标的指针,如:

map< string, unsigned char[]* > WEATHER_ICONS = { 
  { "01d", &icon01d },
  { "01n", &icon01n },
  ...
};

然后(在我的幻想中)能够显示适当的图标,如:

u8g2.drawXBMP( 96, 0, 32, 32, *WEATHER_ICONS[ weatherIcon ] );

weatherIcon是强制转换为字符串的const *char[]
我尝试了各种方法来设置Map:

std::map< std::string, <<variable reference>> > WEATHER_ICONS = { 
  { "01d", &icon01d },
  { "01n", &icon01n }
};

根据表中的<<variable reference>>,我得到各种错误消息:
| 引用的变量已使用|返回错误消息|
| - ------|- ------|
| unsigned char[128]*|template argument 2 is invalid|
| unsigned char[]*|template argument 2 is invalid|
| unsigned char*[128]|x1米11米1x|
| unsigned char*[]|could not convert '{{"01d", (& icon01d)}, {"01n", (& icon01n)}}' from '<brace-enclosed initializer list>' to 'std::map<std::__cxx11::basic_string<char>, unsigned char* []>'|
| unsigned char**|could not convert '{{"01d", (& icon01d)}, {"01n", (& icon01n)}}' from '<brace-enclosed initializer list>' to 'std::map<std::__cxx11::basic_string<char>, unsigned char**>'|
没有一个错误信息对我很有帮助。看起来我已经到达了“c指针地狱”。
我看到了关于stackoverflow的建议,可以定义一个指向指针数组的指针,比如unsigned char**,但是我缺少足够的细节来让它工作。
正确的解决方案是什么?
作为一种解决方案,我已将其实现为:

if     ( strcmp( weatherIcon, "01d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon01d );
      else if( strcmp( weatherIcon, "01n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon01n );
      else if( strcmp( weatherIcon, "02d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon02d );
      else if( strcmp( weatherIcon, "02n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon02n );
      else if( strcmp( weatherIcon, "03d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon03d );
      else if( strcmp( weatherIcon, "03n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon03n );
      else if( strcmp( weatherIcon, "04d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon04d );
      else if( strcmp( weatherIcon, "04n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon04n );
      else if( strcmp( weatherIcon, "09d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon09d );
      else if( strcmp( weatherIcon, "09n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon09n );
      else if( strcmp( weatherIcon, "11d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon11d );
      else if( strcmp( weatherIcon, "11n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon11n );
      else if( strcmp( weatherIcon, "13d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon13d );
      else if( strcmp( weatherIcon, "13n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon13n );
      else if( strcmp( weatherIcon, "50d" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon50d );
      else if( strcmp( weatherIcon, "50n" )==0 ) u8g2.drawXBMP( 96, 0, 32, 32, icon50n );

这很有效,但不是很优雅。

busg9geu

busg9geu1#

在C和C++中,计算数组名会产生指向数组中第一个值的指针。
您的static unsigned char icon01d[]实际上是伪装的unsigned char *。因此:

map< string, unsigned char* > WEATHER_ICONS = { 
  { "01d", icon01d },
  { "01n", icon01n },
  ...
};

从你的问题中还不清楚是否有必要知道每个这样的数组的大小,如果所有这些unsigned char数组大小相同,那么就可以了,否则,也许你可以存储两个数组,像下面这样:

map< string, tuple<unsigned char*, size_t> > WEATHER_ICONS = { 
  { "01d", {icon01d, sizeof(icon01d)} },
  { "01n", {icon01n, sizeof(icon01n)} },
  ...
};
c9qzyr3d

c9qzyr3d2#

在调用drawXBMP的第一个示例中,您有:

u8g2.drawXBMP(96, 0, 32, 32, icon01d);

那么,在这个例子中icon01d是什么?因为你传递的是一个没有索引的数组名,所以你实际上传递的是一个指向数组中第一个元素的指针。在这个例子中,它是一个unsigned char*
当你声明你的map时,你应该使用它,像这样:

map<string, unsigned char*> WEATHER_ICONS = {

那么应该这样调用drawXBMP

u8g2.drawXBMP(96, 0, 32, 32, WEATHER_ICONS[weatherIcon]);
toe95027

toe950273#

看来解决办法是:

std::map< std::string, unsigned char (*)[128] > WEATHER_ICONS = { 
  { "01n", & icon01n },
  { "02d", & icon02d },

别问我怎么知道的。
感谢两位回答这个问题,如果问题不清楚,我很抱歉。

相关问题