Проверка данных на уникальность перед записью в ЕЕПРОМ

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

Приветствую!

Собираю проект "Приемник сигналов с брелков CAME 433.92 MГц." , одно из особенностей данного устройства что оно будет постоянно слушать эфир и собирать коды брелков и записывать их в ЕЕПРОМ. Но перед записью нужно проверить имеющеюся базу на уникальность, другими словами не записывать один и тот же код несколько раз. Прошу помощи в написании данной функции, может у кого уже есть рабочий кусочек кода.

Алгоритм следующий: записать 3 байта в временную ячейку, прочитать первую ячейку ЕЕПРОМ сравнить с первым байтом, если не совпал прочитать 4 ячейку ЕЕПРОМ если совпал прочитать 5 ячейку ЕЕПРОМ сравнить, если совпал сравнить 6 ячейку, если совпал то прекратить сравнение очистить временные рабочие и вернутся к началу, а если не совпал код до последней записанной ячейки то перейти к записи ЕЕПРОМ.

                                         Люди добрые помогите кто чем может!!!!

 

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

Добрые люди верят в вас, и в  то что вы осилите 3-томник Кнут Искусство программирования.

http://mexalib.com/search/?q=%D0%98%D1%81%D0%BA%D1%83%D1%81%D1%81%D1%82%...

ulis
ulis аватар
Offline
Зарегистрирован: 09.03.2011

Н_Андрей_Ю пишет:

                                         Люди добрые помогите кто чем может!!!!

Вам сам алгоритм поиска нужен или как работать с еепром?

По еепрому документации более чем достаточно ...

Что касается алгоритма - отсортируйте уже существующие данные по возрастанию или по убыванию, разделите полученный список пополам (либо по значению, либо по числу элементов - зависит от данных), сравните, ваши новые данные - в какую половину они попадают. Эту половину опять делим пополам и опять смотрим, в какую из уже четвертей попадает ваше значение и так до окончания поиска. Число иттераций примерно будет логарифм по основанию 2 из числа элементов 

toc
Offline
Зарегистрирован: 09.02.2013

Андрей,

>>если не совпал код до последней записанной ячейки

Как отличить записанную ячейку от пустой?

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

toc пишет:
Андрей, >>если не совпал код до последней записанной ячейки Как отличить записанную ячейку от пустой?
Я просто храню в первой и второй ячейки ЕЕПРОМ, номер ячейки с последней записи, тоесть на каком адресе остановился записывать его и записал в первую ячейку и вторую чейку. после отключения питания я востанавливаю адрес читая две первых ячейки!

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

ulis пишет:

Н_Андрей_Ю пишет:

                                         Люди добрые помогите кто чем может!!!!

Вам сам алгоритм поиска нужен или как работать с еепром?

По еепрому документации более чем достаточно ...

Что касается алгоритма - отсортируйте уже существующие данные по возрастанию или по убыванию, разделите полученный список пополам (либо по значению, либо по числу элементов - зависит от данных), сравните, ваши новые данные - в какую половину они попадают. Эту половину опять делим пополам и опять смотрим, в какую из уже четвертей попадает ваше значение и так до окончания поиска. Число иттераций примерно будет логарифм по основанию 2 из числа элементов 

Мне нужен рабочий код функции, читать и писать ЕЕПРОМ я умею, да и написать сам код сравнения я тоже могу, но из за проблемы с головой, ищу может есть уже готовый врагмент который просто отредактирую и вставлю в свой скетч. Я планирую просто сравнивать побайтно, сам код 24 битный, буду сравнивать сначала первый байт, если совпадет тогда буду проверять второй байт, если не совпадет то перейду к следующему коду.

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

qwone пишет:

Добрые люди верят в вас, и в  то что вы осилите 3-томник Кнут Искусство программирования.

http://mexalib.com/search/?q=%D0%98%D1%81%D0%BA%D1%83%D1%81%D1%81%D1%82%D0%B2%D0%BE%20%D0%BF%D1%80%D0%BE%D0%B3%D1%80%D0%B0%D0%BC%D0%BC%D0%B8%D1%80%D0%BE%D0%B2%D0%B0%D0%BD%D0%B8%D1%8F%20%D0%9A%D0%BD%D1%83%D1%82

Грешно смеятся над убогими :(  , я больной на всю голову!  

3-томник Кнут Искусство программирования может и осилю, но не  в этой жизни :(

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

Скажу несколько фактов, которые вы стеснялись спросить: (1) В ЕЕPROM пишется долго, но читается быстро, (2) от чтения в отличии от записи ЕЕPROM не портится. (3) при зашивке скетча , когда не жмешь на кнопку reset ЕЕPROM очищается  от записей. Теперь выводы. Не надо искать конец записи. Запись кончается там где чисто . Смешно !!! Тогда не надо тратить на перезапись 1 и 2 ячейки показывающие конец. Быстрее найти перебором до конца . Если вам надо удалить запись в цепочке поместите 1 и все. Это означает что это пустое место а цепочка продолжается.

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

qwone пишет:

Скажу несколько фактов, которые вы стеснялись спросить: (1) В ЕЕPROM пишется долго, но читается быстро, (2) от чтения в отличии от записи ЕЕPROM не портится. (3) при зашивке скетча , когда не жмешь на кнопку reset ЕЕPROM очищается  от записей. Теперь выводы. Не надо искать конец записи. Запись кончается там где чисто . Смешно !!! Тогда не надо тратить на перезапись 1 и 2 ячейки показывающие конец. Быстрее найти перебором до конца . Если вам надо удалить запись в цепочке поместите 1 и все. Это означает что это пустое место а цепочка продолжается.

Ок, спасибо! Записывать ЕЕПРОМ буду не так часто, А что касаемо адреса последней записаной ячейки, то как определить где свободное место для записи, а так я всегда знаю где остановился счетчик адреса ЕЕПРОМ.В противном случае после включения питания все записи будут начинатся с 3 адреса или нужно добавлять функцию верификации ЕЕПРОМ! 

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

Вот вам стиралка на 255 байт . 

// очистить 256 ячеек

#include <EEPROM.h>
void setup() {
  for (byte i = 0; i <= 256; ++i)  EEPROM.write(i, 0xFF);
}

void loop() {

}

А вот записывалка. В начале выдает вам дамп памяти. Потом вводите В Serial строку и отправляете . РЕСЕТ и смотрите дамп памяти. И да повторно буквы не записывает

// 
#include <EEPROM.h>

void put(char data) {
  int adr = 0;
  char next;
  for (adr = 0; adr < 255; ++adr) {
    next = (char) EEPROM.read(adr);
    if (next == data) break;
    if (next == (char)255) {
      EEPROM.write (adr, data);
      break;
    }
  }
}
void setup() {
  Serial.begin(9600);
  for (int i = 0; i <= 255; ++i) {
    if (i % 16 == 0) {
      Serial.println();
      Serial.print("  ");
      Serial.print(i);
    }
    Serial.print("  ");
    Serial.print(EEPROM.read (i));
  }
}

void loop() {
  if (Serial.available() > 0) {
    char data = (char)Serial.read();
    Serial.println();
    Serial.print(data);
    put(data);
  }
}

 

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

qwone пишет:

Вот вам стиралка на 255 байт . 

// очистить 256 ячеек

#include <EEPROM.h>
void setup() {
  for (byte i = 0; i <= 256; ++i)  EEPROM.write(i, 0xFF);
}

void loop() {

}

А вот записывалка. В начале выдает вам дамп памяти. Потом вводите В Serial строку и отправляете . РЕСЕТ и смотрите дамп памяти. И да повторно буквы не записывает

// 
#include <EEPROM.h>

void put(char data) {
  int adr = 0;
  char next;
  for (adr = 0; adr < 255; ++adr) {
    next = (char) EEPROM.read(adr);
    if (next == data) break;
    if (next == (char)255) {
      EEPROM.write (adr, data);
      break;
    }
  }
}
void setup() {
  Serial.begin(9600);
  for (int i = 0; i <= 255; ++i) {
    if (i % 16 == 0) {
      Serial.println();
      Serial.print("  ");
      Serial.print(i);
    }
    Serial.print("  ");
    Serial.print(EEPROM.read (i));
  }
}

void loop() {
  if (Serial.available() > 0) {
    char data = (char)Serial.read();
    Serial.println();
    Serial.print(data);
    put(data);
  }
}

 

Ок.Спасибо, будем посмотреть, что с этим можно сделать!

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

Посмотрел код в протеусе, по моему то что надо, Как говорится "то что доктор прописал" ! Буду его теперь прилаживать его в основной скетч. посмотрим что получится. Отпишусь! Еще раз Спасибо!

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

Прикрутил ваш код в основной скетч, работает отлично, но теперь встала проблема с структурой бызы банных которая будет хранится в ЕЕПРОМ. 

simmetric
Offline
Зарегистрирован: 27.05.2017

qwone пишет:

Вот вам стиралка на 255 байт . 

// очистить 256 ячеек
#include <EEPROM.h>
void setup() {  for (byte i = 0; i <= 256; ++i)  EEPROM.write(i, 0xFF);}
void loop() {}

прошу прощения за влезание в чужую тему, но похоже на выход за границу индекса. Запишется 257 ячеек вместо 255 тк  i<=256

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

simmetric пишет:

qwone пишет:

Вот вам стиралка на 255 байт . 

// очистить 256 ячеек
#include <EEPROM.h>
void setup() {  for (byte i = 0; i <= 256; ++i)  EEPROM.write(i, 0xFF);}
void loop() {}

прошу прощения за влезание в чужую тему, но похоже на выход за границу индекса. Запишется 257 ячеек вместо 255 тк  i<=256

Вообще размер ЕЕПРОМ 512 байт. писать собираюсь их все от начала до конца поэтому адрес должен быть двух разрядный, но это не проблема!

qwone
qwone аватар
Offline
Зарегистрирован: 03.07.2016

Н_Андрей_Ю пишет:

Прикрутил ваш код в основной скетч, работает отлично, но теперь встала проблема с структурой бызы банных которая будет хранится в ЕЕПРОМ. 

 Вы сами и ответили. Организуйте класс или структуру. К сожалению я вам здесь не помошник. Мне тогда придется переписать всю вашу программу. А это вам или мне надо !!!. http://cpp.com.ru/kr_cbook/ch6kr.html

Н_Андрей_Ю
Н_Андрей_Ю аватар
Offline
Зарегистрирован: 22.12.2016

qwone пишет:

Н_Андрей_Ю пишет:

Прикрутил ваш код в основной скетч, работает отлично, но теперь встала проблема с структурой бызы банных которая будет хранится в ЕЕПРОМ. 

 Вы сами и ответили. Организуйте класс или структуру. К сожалению я вам здесь не помошник. Мне тогда придется переписать всю вашу программу. А это вам или мне надо !!!. http://cpp.com.ru/kr_cbook/ch6kr.html

Про проблему с структурой базы данных я написал не с целью поклянчить помощи, а говоря о том что, работа сдвинулась и перешла на следующий этап. Тут  я постараюсь сам справится, спасибо за ссылку на интересный материал!