#1 2020-05-01 21:59:18

maks.dav
Учасник
Зареєстрований: 2020-05-01
Повідомлень: 1

Запись и чтение из eeprom массивов символов

Имеется следующая задача:

Есть шилд MEGA2560.

Необходимо записать в память EEPROM несколько динамических массивов символов, затем их считать из EEPROM в массивы.

Длина массивов первоначально неизвестна, поэтому они динамические с максимальным количеством элементов (в моём случае 20).

Делается это для экономии оперативной памяти, т.к. работа идёт с большим количеством массивов.

Запись и чтение происходит следующим образом:

#include <EEPROM.h>
char* str = "text";
char* str1;
char* str2;
...
// Выделяем память для str1
str1 = new char[20];
// Вставляем какие-то данные
str1[0] = 'a';
str1[1] = 'b';
str1[2] = 'c';
// Запись в EEPROM str1
EEPROM.put(address1, str1);
// Освобождаем память от str1
delete [] str1;
// Запись в EEPROM str = "text" - статический массив символов
EEPROM.put(address, str);
*****************************************
Перезагружаем контроллер
*****************************************
// Читаем из EEPROM в str1
EEPROM.get(address1, str1); // Читает ерунду
// Читаем из EEPROM в str2
EEPROM.get(address, str2); // Читает нормально - str = "text"!..

Неактивний

#2 2020-05-09 16:58:33

luminofor
Учасник
Зареєстрований: 2020-01-28
Повідомлень: 52

Re: Запись и чтение из eeprom массивов символов

Я как то заморочился подобной проблемой. Было около 50-ти строк по 20-24 символа в каждой
Решил проблему так. Первые 100 адресов EEPROM выделяю под хранение указателей, в которых храниться длина каждой строки.
В остальные записываю текст из массива посимвольно.

#include <EEPROM.h>
#define START_POINTER_ADDRESS 0		// Начальный адрес указателей, исправить при необходимости
#define START_STRING_ADDRESS 100	// Начальный адрес текста, исправить при необходимости
#define HOW_MANY_STRING_TO_SHOW 20	// Сколько строк показывать в Serial
int ptr_addr;	
int strng_addr;

char* text_array [] = 			// Длина каждой строки не должна превышать 255 символов
{
	"Текст кирилицей 0",		//0
	"Текст кирилицей 1",		//1
	"Текст кирилицей 2",		//2
	"Текст кирилицей 3",		//3
	"Текст кирилицей 4",		//4
	"Текст кирилицей 5",		//5
	"Текст кирилицей 6",		//6
	"Текст кирилицей 7",		//7
	"Текст кирилицей 8",		//8
	"Текст кирилицей 9",		//9
	"English Text 0",			//10
	"English Text 1",			//11
	"English Text 2",			//12
	"English Text 3",			//13
	"English Text 4",			//14
	"English Text 5",			//15
	"English Text 6",			//16
	"English Text 7",			//17
	"English Text 8",			//18
	"English Text 9",			//19
};

void setup()
{	
	Serial.begin(9600);
	while ( ! Serial )
	{ // Ждать пока включится сериал, можно удалить

	}
	
	ptr_addr = START_POINTER_ADDRESS;
	strng_addr = START_STRING_ADDRESS;
	
	for (int n=ptr_addr; n<sizeof(text_array)/sizeof(text_array[0]); n++)	// Выражение sizeof(text_array)/sizeof(text_array[0]
	{														// определяет количество символов в строке массива строк 
		String text = text_array[n];						// Выдернуть из массива строк одну строчку
		EEPROM.put(n, text.length()); 						// Записать в EEPROM по адресу n длину строки
		for (int i = 0; i < text.length(); i++)
		{
			EEPROM.write(strng_addr + i, text[i]);				// Записать строчку в EEPROM по одному символу, начиная с начального адреса
		}
		strng_addr += text.length()+1;						// Увеличить начальный адрес на длину предыдущей строки +1
	}														// +1 нужен, чтобы не затереть последний символ предыдущей строки

	strng_addr = START_STRING_ADDRESS;
	
	Serial.println("poiter---length---Text message---");	// Вывод в сериал того, что получилось
	for (int n=0; n<HOW_MANY_STRING_TO_SHOW; n++)			// Перебрать указатели
	{
		Serial.print(n);									// Вывод адрес указателя
		Serial.print("\t");
		Serial.print(strng_addr+EEPROM.read(n));			// Адрес начала строки = адрес старта + длина всех предыдущих строк
		Serial.print("\t");
		for (int i=0; i<EEPROM.read(n); i++)		 		// Вывод символов (количество читается из ячейки n)
		{
			char text[1];									// Объявить массив char с одним символом
			Serial.print(EEPROM.get(i+strng_addr,text));	// Вывести один символ
		}
		Serial.println("");
		strng_addr += (1+EEPROM.read(n));					// Начало следующей строки = длина предыдущей строки +1
	}														// +1 по той же причине, что и выше

}

void loop()
{

}

Вот видос того, что получается

Неактивний

#3 2020-05-09 21:44:15

Kaka
Учасник
Зареєстрований: 2018-03-21
Повідомлень: 411

Re: Запись и чтение из eeprom массивов символов

Еще одно доказательство, что наш народ ничем не напугать. Хочешь штаны через голову? - Легко!

Неактивний

Швидке повідомлення

Введіть повідомлення і натисніть Надіслати

Підвал форуму