Несовместимые типы при назначении «uint8_t {aka unsigned char}» на «uint8_t [1] {aka unsigned char [1]}»
Я пытаюсь отправить пользовательские данные. Но, похоже, это не работает. Я не могу найти способ разобрать мою строку на unit8_t. Я пытался следовать решениям других людей, но они мне не подходят.
// Declaration
uint8_t myData[] = "";
void loop(){
myData = *(uint8_t*)atoi("custom string".c_str());
}
Это сообщение об ошибке, которое я постоянно получаю: Несовместимые типы при назначении uint8_t {aka unsigned char}' на 'uint8_t [1] {aka unsigned char [1]} .
@Mounir Mehjoub, 👍0
Обсуждение3 ответа
Лучший ответ:
atoi
предназначен для преобразования текстового представления числа (например, "123") в фактическое целое число.
Функция c_str() дает вам указатель на внутренний буфер строки (при условии, что у вас действительно есть строка), который ничем не отличается от uint8_t[]
или uint8_t *
(кроме подписи).
Не зная точно, что требуется функции назначения для этого буфера, очень трудно вам помочь, но вы можете захотеть что-то вроде:
LoRaWan.send((uint8_t *)myString.c_str(), myString.length());
Если вам нужно скопировать данные в буфер фиксированной длины, вам нужно сначала создать буфер этого фактического размера, а затем скопировать в него строковые данные:
// Создаем буфер размером 32 байта
uint8_t myBuffer[32];
// Копируем в буфер не более 32 байт, но не больше, чем есть на самом деле
memcpy(myBuffer, myString.c_str(), min(myString.length(), 32));
Я использовал ваш метод и удалил метод atoi
. Теперь я понимаю методы намного больше. Я также добавил указатель к моей переменной объявления, такой как uint8_t* myData[2];, @Mounir Mehjoub
Это фактически создаст массив из двух неназначенных указателей, а не указатель на массив из 2 байтов., @Majenko
@MounirMehjoub Это может помочь: https://majenko.co.uk/blog/arrays-pointers-what-c, @Majenko
В вашем коде беспорядок. Очевидно, вы сильно путаетесь между массивами, указателями и строками C++.
Когда вы говорите
uint8_t myData[] = "";
вы создаете myData типа "массив uint8_t" и содержите пустую строку. В этом случае вам не следует изменять это значение.
Когда вы говорите
uint8_t *myData;
это означает, что myData
является переменной типа "указатель на uint8_t", но пока ни на что не указывает.
Этим объявлением вы позже сможете сказать:
myData = "custom string";
Это указывает указатель myData
на адрес вашей постоянной строки. Я думаю, это то, что вы хотите:
// Декларация
uint8_t *myData;
void loop(){
myData = "custom string";
}
Да, мне жаль, @Duncan C, ты прав. Я не очень разбираюсь в С++ с указателями. Итак, я попробовал ваше решение, но оно снова дало ошибку. не может преобразовать 'String' в 'uint8_t* {aka unsigned char*}' при назначении. Что я пытаюсь сделать, так это преобразовать пользовательскую строку в uint8_t, чтобы я мог отправить ее по LoRaWAN. Метод отправки сообщений LoRaWAN, который я использую, имел uint8_t в качестве параметра., @Mounir Mehjoub
Относительно «_Вам не следует изменять это значение_»: Нет проблем с изменением этого значения. Просто имейте в виду, что это массив длины 1., @Edgar Bonet
Во-первых, массивы в C и C++ нельзя присваивать. Таким образом, ваши попытки присвоить что-то массиву myData
с оператором =
обречены на провал в любом случае. Копирование данных в голые массивы следует выполнять либо вручную, либо с помощью библиотечных функций.
Во-вторых, ваш массив myData
объявлен с размером 1
. Это всего лишь один байт. Он слишком мал, чтобы хранить что-то полезное. Он не будет волшебным образом «растягиваться» сам по себе, чтобы вместить больше данных. Если вам нужно хранить больше данных в этом массиве, вы обязаны заранее объявить соответствующий размер.
В-третьих, что означает "custom string".c_str()
??? Что-то очень похожее на это может быть выражено в современном C++ как
#include <string>
...
using namespace std::string_literals;
"custom string"s.c_str();
но я вообще не вижу для этого причин. Если вы вводите C-строку, то функция atoi
напрямую применима к C-строке. Нет необходимости преобразовывать такую C-строку в std::string
и обратно.
В-четвертых, atoi
— это «мертвая» функция, которая существует только для совместимости с устаревшим кодом. Вы не должны использовать atoi
в своем коде. Функции преобразования строки в число в стиле C — это функции из группы strto...
. Например, strtol
в вашем случае. Но в C++ у вас могут быть варианты получше, например std::stoi
и тому подобное.
- C++ против языка Arduino?
- ошибка: ожидаемое первичное выражение перед токеном ','
- Ввести идентификатор чипа ESP32 в строковую переменную (новичок в Arduino/C++)
- Передача функции-члена класса в качестве аргумента
- Улучшенное циклическое переключение цветов RGB.
- Какие есть другие IDE для Arduino?
- Как преобразовать массив символов в строку в arduino?
- Каково отношение файла Arduino .ino к main.cpp?
Что вы там пытаетесь сделать? Вы пытаетесь преобразовать текстовое представление числа в фактическое число или поместить немного текста в буфер uint8_t?, @Majenko
Таким образом, вы создаете объект C++ String из литерала C-String, затем извлекаете из него C-String и пытаетесь проанализировать из него число (которое он не содержит). Имеет для меня полный смысл...., @Kwasmich
@Majenko Я пытаюсь поместить немного текста в буфер uint8_t, потому что пытаюсь отправить данные по сети LoRaWAN. Если я объявлю myData[] как myData[] = "Test data"; Он отправляет по сети без ошибок компиляции. Когда я пытаюсь поместить строку в myData после прохождения настройки и в моем цикле, похоже, я не могу добавить это так же просто, как myData = "Custom String";, @Mounir Mehjoub
Что означает «пользовательская строка».c_str()
? В современном C++ вы можете использовать
"пользовательскую строку" s.c_str(), но только если вы сначала используете
используя пространство имен std::string_literals;`., @AnT