使用strtok并获取"无法转换' char *' to' char **'在作业"

时间:2018-02-04 00:49:46

标签: c++ arduino strtok

我正在尝试创建一个程序,该程序从SPIFFS中的文件中读取一个字符串,其中包含4个以制表符分隔的内容,然后将其处理为四个char数组,以便在另一个函数中使用。但是,我收到错误cannot convert 'char*' to 'char**' in assignment。有什么想法吗?这是我的代码:

#include <string.h>
#include "FS.h"
#include "AdafruitIO_WiFi.h"
char *ssid;
char *pass;
char *aiduser;
char *aidkey;
// comment out the following two lines if you are using fona or ethernet
#include "AdafruitIO_WiFi.h"
//AdafruitIO_WiFi io(IO_USERNAME, IO_KEY, WIFI_SSID, WIFI_PASS);
void setupWifi(char* *aiduser, char* *aidkey, char* *ssid, char* *pass){

#define WIFIFILE "/config.txt"
int addr = 0;
bool spiffsActive = false;

if (SPIFFS.begin()) {
      spiffsActive = true;
 }
 File f = SPIFFS.open(WIFIFILE, "r");
 String str;
 while (f.position()<f.size())
        {
          str=f.readStringUntil('\n');
          str.trim();
        } 

// Length (with one extra character for the null terminator)
int str_len = str.length() + 1; 

// Prepare the character array (the buffer) 
char char_array[str_len];

// Copy it over 
str.toCharArray(char_array, str_len);
   const char s[2] = {9, 0};

   /* get the first token */
   aiduser = strtok(char_array, s);
   aidpass = strtok(NULL, s);
   ssid = strtok(NULL, s);
   pass = strtok(NULL, s);

   /* walk through other tokens 
   while( token != NULL ) {
      printf( " %s\n", token );

      token = strtok(NULL, s);
   }*/
   // RESULT: A thingy
}

void setup(){
setupWifi(&aiduser, &aidkey, &ssid, &pass);

AdafruitIO_WiFi io(aiduser, aidkey, ssid, pass);}

此外,我无法运行setupWifi功能,除非它处于设置或循环中,但我无法在另一个设置中进行,因为这是#included到另一个主文件中。

1 个答案:

答案 0 :(得分:1)

由于这个原因,您收到此错误:

 Sub GetUnmatchedRecords()

 Dim sQuery As String, sFileName  as String
 Dim conn As New ADODB.Connection
 Dim rs As New ADODB.Recordset

 sFileName = ThisWorkbook.FullName
 sConnection = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=""" & _
   sFileName & """;Extended Properties=""Excel 12.0 Xml;HDR=YES;IMEX = 1"""

 Conn.Open sConnection 

 sQuery = "SELECT id1,name1 From [Sheet1$] where id1+name1 not in (SELECT id2+name2 from [Sheet1$])"
 rs.Open sQuery , Conn

 Sheet1.Range("E2").CopyFromRecordset rs
 rs.Close
 conn.Close

End Sub

这个变量是双指针,void setupWifi(char* *aiduser, char* *aidkey, char* *ssid, char* *pass) { ... aiduser = strtok(char_array, s); aidpass = strtok(NULL, s); ssid = strtok(NULL, s); pass = strtok(NULL, s); } 返回指向strtok的指针 是不兼容的类型。

因为char返回strtokchar_array + some_offset是本地的 char_array中的变量,你需要为每个变量做一个副本并返回 复制而不是。您可以使用setupWifi

执行此操作
strdup

我建议您始终检查 *aiduser = strdup(strtok(char_array, s)); *aidpass = strdup(strtok(NULL, s)); *ssid = strdup(strtok(NULL, s)); *pass = strdup(strtok(NULL, s)); 的返回值,因为它可以 返回strdup 1

如果您的系统没有NULL,那么您可以自己编写:

strdup

最后一件事:

char *strdup(const char *text)
{
    if(text == NULL)
        return NULL;

    char *copy = calloc(strlen(text) + 1, 1);
    if(copy == NULL)
        return NULL;

    return strcpy(copy, text);
}

看起来真的很尴尬,从未见过用这种方式声明双指针。许多 更容易阅读

void setupWifi(char* *aiduser, char* *aidkey, char* *ssid, char* *pass);

<强> Fotenotes

1 虽然语法正确,但我仍然认为这是一种不好的做法, 因为您应该始终检查返回的函数的返回值 指针。如果他们返回void setupWifi(char **aiduser, char **aidkey, char **ssid, char **pass); ,则无法访问内存。这增加了一个 一点点代码,但你的程序不会死于段错误,它可以 从错误中恢复。

我也将你的功能改为成功时返回1,否则改为0:

NULL