物联网开发Arduino_EEPROM_Esp8266断电存储实例

查询了很多资料,反复尝试总出现各种错误。目前针对结构体参数存储数据到EEPROM进行了尝试和总结,以便学习使用。

废话少说:直接代码并注解!【首发于头条,转发于此,更多资源关注,久爱物联网】

重点

1、写要提交,方法不能遗漏!EEPROM.end();或EEPROM.commit();必具其一,建议前者

2、内存空间申请大小必须大于结构体数据长度(4的倍数) 如:EEPROM.begin(128);

3、存储地址不能重叠,且有效利用!!寸土是金!上一数据地址+1开始

/*****************************************************
调用#include <EEPROM.h>来使用EEPROM;
使用EEPROM时,首先调用EEPROM.begin(size),size为需要读写的数据字节最大地址+1,取值4~4096;
使用EEPROM.write(addr,data)来写数据,参数分别为地址&数据,写数据后需要通过EEPROM.commit()或EEPROM.end()将数据保存到EEPROM;
使用EEPROM.read(addr)来读数据;


*久爱物联网(jiuaiiot)* 注意事项 * 
当你需要分多次写EEPROM时,切记之后每次EEPROM.begin(size);中输入的size必须大于等于之前每次输入的值。
简单点的话可以每次写入时这里都输入你可能会用到的最大值,比如如果对时间和内存要求不高的话这里可以写死4096。
你每次操作EEPROM,根据你输入的size,会建立一个size大小的缓存并从EEPROM地址0开始读取size长度数据到该缓存,你之后的读写操作是对这个缓存的操作。
当你提交写入的时候,程序才会把缓存中的数据写入EEPROM,但是EEPROM的写入是以扇区为单位的(4096字节)
那么在写入的时候从地址0开始的size个数数据时ok的,但后面4096-size个数据就可能会被改变(我目前遇到的就是后面的数据都变255了)。
这应该是这个库的一个逻辑bug。因为ESP8266的EEPROM并非真正的EEPROM,只是从flash上划了一个扇区用,所以读写都只能按扇区来。
******************************************************/
//引用头文件
#include <EEPROM.h>
//定义一个写和读的通用方法
#define EEPROM_write(address,p) { int i = 0;byte *pp = (byte*)&(p);for(;i<sizeof(p);i++) EEPROM.write(address+i,pp[i]);EEPROM.end();}
#define EEPROM_read(address,p) { int i = 0;byte *pp = (byte*)&(p);for(;i<sizeof(p);i++) pp[i]=EEPROM.read(address+i);}
//注意事项 写的结尾一定要有EEPROM.end();或EEPROM.commit();目的就是提交保存操作否则不保存成功

//测试2个结构体不同的存储地地址
struct config_type
{//sizeof(config_type)=72
  int date1;
  float date2;
  char date3[64];
}cfgtype;//声明别名cfgtype
//结构体2
struct config_jiuai
{//sizeof(config_jiuai)=128
  char jiuai[128];
}cfgjiuai;//声明别名cfgjiuai

void eeprom_test() {
  Serial.println(sizeof(cfgtype));//72
  cfgtype.date1 = 6266;
  cfgtype.date2 = 3.14;
  strcpy(cfgtype.date3, "{\"fuwuhao\":\"jiuaiiot\",\"tel\":\"180***77\"}");// 标准json字符串;赋值方法strcpy() 
  EEPROM.begin(128);//申请内存空间
  EEPROM_write(0, cfgtype);  //写入到0地址的结构体变量
  //-------结构体1写结束-------------
  EEPROM.begin(256);//申请空间必须大于结构体长度,4的倍数
  sprintf(cfgjiuai.jiuai,"{\"tel\":\"%s\",\"mode\":%d,\"automode\":%d}","180***66",1,0);
  //赋值方法 标准json格式
  Serial.println(sizeof(cfgjiuai));
  EEPROM_write(129, cfgjiuai);//写地址128+1 结构体2
  //EEPROM.commit();  //上方法中提交
  Serial.println("write ok!");
  //-----------结构体1读------------
  config_type readback;//结构体变量(读)
  EEPROM.begin(128);//申请内存空间
  EEPROM_read(0, readback);  //从地址0读取数据
  Serial.print("data1:");
  Serial.println(readback.date1);//打印数据1
  Serial.print("data2:");
  Serial.println(readback.date2);
  Serial.print("data3:");
  Serial.println(readback.date3);//打印数据3
  //------------结构体2读----------------
  EEPROM.begin(256);//申请空间
  config_jiuai jiuai1;//申请变量
  EEPROM_read(129, jiuai1);//读数据
  Serial.print("jiuai:");
  Serial.println(jiuai1.jiuai);//打印数据
  
  Serial.println("read eeprom over!");
}

void setup() {
  Serial.begin(9600);//波特率9600和115200均可
  eeprom_test();//读和写
}

void loop() {
  //欢迎关注 订阅,学习开发板即将发布!
}

学习2种赋值方法:strcpy()  和 sprintf() 

物联网开发Arduino_EEPROM_Esp8266断电存储实例

更多学习实践,全部实践后的总结。更多精彩敬请关注!!有惊喜哦

物联网开发Arduino_EEPROM_Esp8266断电存储实例

 物联网开发Arduino_EEPROM_Esp8266断电存储实例物联网开发Arduino_EEPROM_Esp8266断电存储实例

物联网开发Arduino_EEPROM_Esp8266断电存储实例

猜你喜欢

转载自blog.csdn.net/uaime/article/details/106952256