主函数:

四极管:main.c

#include<avr/io.h>
#include<util/delay.h>
#include<1602driver.c>
#include<24c64.c>
int  main(void)
{
 uchar const data[]="0123456789";
uchar data_from_24c64=0;
Init_1602();
Write_24c64(0x0000,000);
_delay_ms(10);
Displaypstr(0,1,"oh h!");
DDRA=0Xff;
PORTA=0X0f;
data_from_24c64=Read_24c64(0x0000);
while(1)
{
Displaychar(0,0,data[data_from_24c64/100]);
Displaychar(1,0,data[(data_from_24c64%100)/10]);
Displaychar(2,0,data[data_from_24c64%10]);
_delay_ms(100);
}
return  0;
}

四极管:24c64驱动(24C64.c)

/***********************************
函数功能:24c64读写操作
使用环境:    硬件: MCU: ATmega32L
F_CPU = 16000000
外部:16000000
接线方法:A0/A1/A2接地;WP接地;scl/sda接接10k上拉电阻后接任意两个IO口
编译环境:WinAVR-20080610
使用说明:  24c64容量为64kbit  采用线性连续排列,地址空间为0000H-FFFFFH
地址长度为16位  两字节
在24c64内部:把64kbit分为2048页,每页32字节,页内偏移量(低五位):0--31(0x00--0x1f)
页码(高11位):页码:0-2047(0x20---0xffff)
写操作:
1、字节写:(0x00--0x1f)
2、页  写:(0x20---0xffff)
读操作:
1、字节读:(0x00--0x1f)
2、页  读:(0x20---0xffff)  
作者:杨琦
日期:2009年7月26日
修改者:                 (日期:  )
*******************************************************************/
//端口定义
#define  SDA_1() {DDRB|=(1<<0);PORTB|=(1<<0);}
#define  SDA_0() {DDRB|=(1<<0);PORTB&=~(1<<0);}
#define  SCL_1() {DDRB|=(1<<1);PORTB|=(1<<1);}
#define  SCL_0() {DDRB|=(1<<1);PORTB&=~(1<<1);}
#define uint  unsigned int
#define uchar unsigned char
/*---------------IIC总线操作流程-----------------------------------------
*  一、 写操作顺序:
*    启动总线→写器件地址→写单元地址→写数据→. . .→关闭总线
*    器件地址组成:固定地址(厂家)+外部连线地址+1位读写地址(1:读 ,0:写)
*  二、 指定单元读操作:
*    启动总线→写器件地址→写单元地址→启动总线→写入要读出的器件地址→
*    读数据→. . .→关闭总线
*  三、 当前单元读操作
*    启动总线→写入要读出的器件地址→读数据→. . .→关闭总线
------------------------------------------------------------------------*/
/*---------------IIC总线器件地址-----------------------------------------
*  IIC总线地址格式:1010XXXX
*  地址说明:
*        BIT7-BIT4:IIC总线地址高4位固定为1010,即10进制A
*        BIT3-BIT1:地址为生产厂家规定地址,如PCF8563为001,24C系列为000
*        BIT0     :读写控制位,0:写操作;1:读操作
------------------------------------------------------------------------*/
/****************************************
** 函数名:延时子函数                   *
** 功  能:稍作延时                     *
** 子函数:无                           *
** 变  量:uint time                    *
** 返回值:无                           *
****************************************/
void DelayMS(uint time)
{
do
{
time--;
}
while(time);
}
/****************************************
** 函数名:启动器件子程序               *
** 功  能:I2C启动总线                  *
** 子函数:DelayMs();                   *
** 变  量:无                           *
** 返回值:无                           *
****************************************/
void  Start_24c64(void)
{
SDA_1();
DelayMS(2);
SCL_1();
DelayMS(2);
SDA_0();
DelayMS(8);
SCL_0();
DelayMS(2);
}
/****************************************
** 函数名:停止器件子程序               *
** 功  能:I2C启动总线                  *
** 子函数:DelayMs();                   *
** 变  量:无                           *
** 返回值:无                           *
****************************************/
void Stop_24c64(void)
{
SDA_0();
DelayMS(2);
SCL_0();
DelayMS(2);
SCL_1();
DelayMS(2);
SDA_1();
DelayMS(8);
SCL_0();
DelayMS(2);
}
/*********************************************
** 函数名:主机发送一个字节数据至24c64子程序 *
** 功  能:向24c64写一个字节,从高位开始     *
** 子函数:DelayMs();                        *
** 变  量:uchar bytedata                    *
** 返回值:uchar                             *
**********************************************/
uchar SendByte_24c64(uchar bytedata)
{
uchar i;
uchar flag=0;
SCL_0();
DelayMS(4);
for(i=0;i<8;i++)
{
if(bytedata&0x80)
{
SDA_1();
}
else
{
SDA_0();
}
DelayMS(2);
SCL_1();
DelayMS(2);
bytedata<<=1;
SCL_0();
DelayMS(2);
}
SDA_1();
DelayMS(2);
DDRB&=~(1<<0);
SCL_1();
DelayMS(1);
if(!(PINB&(1<<0)))
{
flag=1;
}
DDRB|=(1<<0);
SCL_0();
DelayMS(2);
return(flag);
}
/*********************************************
** 函数名:主机接收一个字节子程序从高位开始读*
** 功  能:读取24c64一个字节,从高位开始读    *
** 子函数:DelayMs();                        *
** 变  量:uchar ack                         *
** 返回值:uchar                             *
**********************************************/
uchar ReceiveByte_24c64(uchar ack)
{
uchar i,a=0;
SCL_0();
for(i=0;i<8;i++)
{
SDA_1();
DelayMS(2);
a<<=1;
DDRB&=~(1<<0);
SCL_1();
DelayMS(2);
if(PINB&(1<<0))
{
a++;
}
SCL_0();
DelayMS(2);
}
DDRB|=(1<<0);
if(!ack)
{
SDA_1();
}
else
{
SDA_0();
}
SCL_1();
DelayMS(2);
SCL_0();
DelayMS(2);
return(a);
}
/*********************************************************
** 函数名:向24c64写如数据                               *
** 功  能:向24c64写入其地址和数据                       *
** 子函数:Start_24c64();SendByte_24c64();Stop_24c64();  *
** 变  量:uint Address, uchar Data                      *
** 返回值:无                                            *
*********************************************************/
void Write_24c64(uint Address, uchar Data)
{
uchar flag1=0,flag2=0,flag3=0,flag4=0;
Start_24c64();   //启动总线
flag1=SendByte_24c64(0xa0);  //写器件地址 确保最低位(w/R)位为0
DelayMS(5);
if(flag1==1)
{
flag2=SendByte_24c64((Address&0xff00)>>8);//写单元地址高位
DelayMS(5);
if(flag2==1)
{
flag3=SendByte_24c64(Address&0xff);//写单元地址低位
DelayMS(5);
if(flag3==1)
{
flag4=SendByte_24c64(Data); //写数据
DelayMS(5);
}
}
}
Stop_24c64();    //停止总线
}
/**************************************************************************
** 函数名:从24c64读取数据                                                *
** 功  能:向24c64指定地址读取数据                                        *
** 子函数:Start_24c64();SendByte_24c64();ReceiveByte_24c64Stop_24c64();  *
** 变  量:uint Address                                                   *
** 返回值:uchar                                                          *
***************************************************************************/
uchar Read_24c64(uint Address) //分为立即读和选择读
{
uchar flag1=0,flag2=0,flag3=0,flag4=0;
uchar readdata=0;
Start_24c64();     // 开启总线
flag1=SendByte_24c64(0xa0);  //写器件地址(写操作)
DelayMS(5);
if(flag1==1)
{
flag2=SendByte_24c64((Address&0xff00)>>8);//写单元地址高位
DelayMS(5);
if(flag2==1)
{
flag3=SendByte_24c64(Address&0xff);//写单元地址低位
DelayMS(5);
if(flag3==1)
{
Start_24c64();    //启动总线
flag4=SendByte_24c64(0xa1);   //写器件地址(读操作)
DelayMS(5);
if(flag4==1)
{
readdata=ReceiveByte_24c64(1);    //读数据
DelayMS(5);
}
}
}
}
Stop_24c64();
return(readdata);
}

四极管:液晶显示驱动(1602driver.c)

/***********************************
函数功能:1602 液晶显示两行数字和字符
函数说明:四线方式,数据输出线:DATA_PORT
使用环境:    硬件: MCU: ATmega32L
F_CPU = 16000000
外部:16000000
接线方法:3跟数据线:PC1-RS   PC2-RW  PC3-E
4跟数据线:PC
编译环境:WinAVR-20080610
显示说明:
显示字符函数:
Displaychar(unsigned char x,unsigned char y, unsigned char wdata)
(x为横坐标   y为坐标 wdata为所要显示的东西)
显示字符串函数:
Displaypstr(unsigned char x,unsigned char y,unsigned char *str)
(x为横坐标   y为坐标  wdata为所要显示的东西)
坐标定位说明:X:0-15
Y:0-1
包含文件 :MyBit.h    
 作者:杨琦
日期:2009年7月13日
修改者:                 (日期:  )
***********************************/
//管脚定义
#define DATA_PORT PORTC
#define RS_0() {DDRC |=(1<<1);PORTC &=~(1<<1);}
#define RS_1() {DDRC |=(1<<1);PORTC |= (1<<1);}
#define RW_0() {DDRC |=(1<<2);PORTC &=~(1<<2);}
#define RW_1() {DDRC |=(1<<2);PORTC |= (1<<2);}
#define E_0()  {DDRC |=(1<<3);PORTC &=~(1<<3);}
#define E_1()  {DDRC |=(1<<3);PORTC |= (1<<3);}
#define budy_in()   {DDRC&=~(1<<7);PORTC|=(1<<7);}
#define budy_high    PINC&(1<<7)
#define busy_out()   {DDRC|=(1<<7);}
//注:读忙函数需对输出口最高位进行设置和判断
/****************************************
** 函数名:readbusy
** 功能  :读忙函数
** 子函数:无
** 变量  :无
----------------------------------------
****************************************/
void readbusy(void)
{
//检测忙位改为输入
budy_in();//拉高
RW_1();
RS_0();
E_1();
while(budy_high);//等待为低电平   ????????@@@@@@
E_0();
busy_out();
}
/****************************************
** 函数名:sentbyte
** 功能  :发送一节数
** 子函数:readbusy()
** 变量  :数据或命令 tybe=1数据 0命令
----------------------------------------
****************************************/
void sentbyte(unsigned char i,unsigned char tybe)
{
unsigned char temp;
readbusy();
if(tybe == 1)
{
RW_0();
RS_1();
}
if(tybe == 0)
{
RW_0();
RS_0();
}
temp = i&0xf0;
DATA_PORT &=0x0f;
DATA_PORT |=temp;
E_1();
E_0();
temp = (i<<4)&0xf0;
DATA_PORT &=0X0f;
DATA_PORT |=temp;
E_1();
E_0();
}
/****************************************
** 函数名:Init_1602()
** 功能  :初始化1602液晶显示
** 变量  :无
----------------------------------------
****************************************/
void Init_1602(void)
{
DDRC = 0xff;
sentbyte(0x30,0);
sentbyte(0x30,0);
sentbyte(0x30,0);
sentbyte(0x02,0);
sentbyte(0x28,0);   //设置工作方式:4位总线字符两行0x28,8位总线字符两行0x38
sentbyte(0x01,0);  //清屏
sentbyte(0x02,0);   //数据指针清零
sentbyte(0x0c,0);   //开光标,但光标不闪
sentbyte(0x06,0);   //写字符后光标加一
sentbyte(0x01,0);   //清屏
}
/****************************************
** 函数名:Locate_xy()
** 功能  :写地址
** 变量  :x,y
----------------------------------------
****************************************/
void Locate_xy(unsigned char x,unsigned char y )
{
unsigned char addr=0;
if(y == 0)addr=0x80+x;
if(y == 1)addr=0xc0+x;
sentbyte(addr,0);
}
/****************************************
** 函数名:Displaychar()
** 功能  :1602液晶显示一个字符
** 变量  :x,y,wdata
----------------------------------------
****************************************/
void Displaychar(unsigned char x,unsigned char y,
unsigned char wdata)
{
Locate_xy(x,y);
sentbyte(wdata,1);
}
/****************************************
** 函数名:Displaypstr()
** 功能  :1602液晶显示一个字符串
** 变量  :x,y,*str
----------------------------------------
****************************************/
void Displaypstr(unsigned char x,unsigned char y,unsigned char *str)
{
unsigned int i=0;
Locate_xy(x,y);
while(str[i]!='\0')
{
sentbyte(str[i++],1);
x++;
if(x>15)
{
x=0;
y++;
if(y==2)y=0;
Locate_xy(x,y);
}
}
}
头文件定义(MyBit.h)
/***********************************************************
文件名称:位操作头文件
File :MyBit.h
功能描述:通过位段定义的方法,把位从字节中分离成
位变量,即可对端口或一般寄存器进行位操作
使用范例:
A口0脚输出高电平: OA0=1;
读取A口1脚电平: while(IA1);
设置A口2脚为输出: RA2=1;
创建日期:2007-2-14
Author :廖志贤
***********************************************************/

typedef struct
{
unsigned  bit0: 1 ;
unsigned  bit1: 1 ;
unsigned  bit2: 1 ;
unsigned  bit3: 1 ;
unsigned  bit4: 1 ;
unsigned  bit5: 1 ;
unsigned  bit6: 1 ;
unsigned  bit7: 1 ;
}PORTtype,Byte;

typedef struct
{
unsigned  bit0: 1 ;
unsigned  bit1: 1 ;
unsigned  bit2: 1 ;
unsigned  bit3: 1 ;
unsigned  bit4: 1 ;
unsigned  bit5: 1 ;
unsigned  bit6: 1 ;
unsigned  bit7: 1 ;
unsigned  bit8: 1 ;
unsigned  bit9: 1 ;
unsigned  bit10: 1 ;
unsigned  bit11: 1 ;
unsigned  bit12: 1 ;
unsigned  bit13: 1 ;
unsigned  bit14: 1 ;
unsigned  bit15: 1 ;
}Word;
/*************************************************
IO位定义开始
*************************************************/

//************************************************

//定义A口端口数据寄存器,等同于PORTA
#define A_OUT (*(volatile PORTtype *)(0x1B+0x20))
//定义A口端口方向寄存器,等同于DDRA
#define A_DIR (*(volatile PORTtype *)(0x1A+0x20))
//定义A口端口输入寄存器,等同于PINA
#define A_DIN (*(volatile PORTtype *)(0x19+0x20))

//定义B口端口数据寄存器,等同于PORTB
#define B_OUT (*(volatile PORTtype *)(0x18+0x20))
//定义B口端口方向寄存器,等同于DDRB
#define B_DIR (*(volatile PORTtype *)(0x17+0x20))
//定义B口端口输入寄存器,等同于PINB
#define B_DIN (*(volatile PORTtype *)(0x16+0x20))

//定义C口端口数据寄存器,等同于PORTC
#define C_OUT (*(volatile PORTtype *)(0x15+0x20))
//定义C口端口方向寄存器,等同于DDRC
#define C_DIR (*(volatile PORTtype *)(0x14+0x20))
//定义C口端口输入寄存器,等同于PINC
#define C_DIN (*(volatile PORTtype *)(0x13+0x20))

//定义D口端口数据寄存器,等同于PORTD
#define D_OUT (*(volatile PORTtype *)(0x12+0x20))
//定义D口端口方向寄存器,等同于DDRD
#define D_DIR (*(volatile PORTtype *)(0x11+0x20))
//定义D口端口输入寄存器,等同于PIND
#define D_DIN (*(volatile PORTtype *)(0x10+0x20))

//************************************************

//预定义口位OAX----大写字母O表示output,表明
//这种表示对应PORTA的使用方法,即输出寄存器,以
//数字X为第X位
//下OBX,OCX,ODX为相同意义

//预定义口位RAX----大写字母R表示rudder(方向舵),
//表明这种表示对应DDRA的使用方法,即用于设置端
//口方向,以下RBX,RCX,RDX为相同意义

//预定义口位IAX----大写字母I表示input,表明
//这种表示对应PINA的使用方法,即读取端口电平,
//以下IBX,ICX,IDX为相同意义

//-----------------------************************
//输出数据

#define OA0 A_OUT.bit0
#define OA1 A_OUT.bit1
#define OA2 A_OUT.bit2
#define OA3 A_OUT.bit3
#define OA4 A_OUT.bit4
#define OA5 A_OUT.bit5
#define OA6 A_OUT.bit6
#define OA7 A_OUT.bit7

#define OB0 B_OUT.bit0
#define OB1 B_OUT.bit1
#define OB2 B_OUT.bit2
#define OB3 B_OUT.bit3
#define OB4 B_OUT.bit4
#define OB5 B_OUT.bit5
#define OB6 B_OUT.bit6
#define OB7 B_OUT.bit7

#define OC0 C_OUT.bit0
#define OC1 C_OUT.bit1
#define OC2 C_OUT.bit2
#define OC3 C_OUT.bit3
#define OC4 C_OUT.bit4
#define OC5 C_OUT.bit5
#define OC6 C_OUT.bit6
#define OC7 C_OUT.bit7

#define OD0 D_OUT.bit0
#define OD1 D_OUT.bit1
#define OD2 D_OUT.bit2
#define OD3 D_OUT.bit3
#define OD4 D_OUT.bit4
#define OD5 D_OUT.bit5
#define OD6 D_OUT.bit6
#define OD7 D_OUT.bit7

//--------------------***************************
//设置方向

#define RA0 A_DIR.bit0
#define RA1 A_DIR.bit1
#define RA2 A_DIR.bit2
#define RA3 A_DIR.bit3
#define RA4 A_DIR.bit4
#define RA5 A_DIR.bit5
#define RA6 A_DIR.bit6
#define RA7 A_DIR.bit7

#define RB0 B_DIR.bit0
#define RB1 B_DIR.bit1
#define RB2 B_DIR.bit2
#define RB3 B_DIR.bit3
#define RB4 B_DIR.bit4
#define RB5 B_DIR.bit5
#define RB6 B_DIR.bit6
#define RB7 B_DIR.bit7

#define RC0 C_DIR.bit0
#define RC1 C_DIR.bit1
#define RC2 C_DIR.bit2
#define RC3 C_DIR.bit3
#define RC4 C_DIR.bit4
#define RC5 C_DIR.bit5
#define RC6 C_DIR.bit6
#define RC7 C_DIR.bit7

#define RD0 D_DIR.bit0
#define RD1 D_DIR.bit1
#define RD2 D_DIR.bit2
#define RD3 D_DIR.bit3
#define RD4 D_DIR.bit4
#define RD5 D_DIR.bit5
#define RD6 D_DIR.bit6
#define RD7 D_DIR.bit7

//----------------------**************************
//读取端口

#define IA0 A_DIN.bit0
#define IA1 A_DIN.bit1
#define IA2 A_DIN.bit2
#define IA3 A_DIN.bit3
#define IA4 A_DIN.bit4
#define IA5 A_DIN.bit5
#define IA6 A_DIN.bit6
#define IA7 A_DIN.bit7

#define IB0 B_DIN.bit0
#define IB1 B_DIN.bit1
#define IB2 B_DIN.bit2
#define IB3 B_DIN.bit3
#define IB4 B_DIN.bit4
#define IB5 B_DIN.bit5
#define IB6 B_DIN.bit6
#define IB7 B_DIN.bit7

#define IC0 C_DIN.bit0
#define IC1 C_DIN.bit1
#define IC2 C_DIN.bit2
#define IC3 C_DIN.bit3
#define IC4 C_DIN.bit4
#define IC5 C_DIN.bit5
#define IC6 C_DIN.bit6
#define IC7 C_DIN.bit7

#define ID0 D_DIN.bit0
#define ID1 D_DIN.bit1
#define ID2 D_DIN.bit2
#define ID3 D_DIN.bit3
#define ID4 D_DIN.bit4
#define ID5 D_DIN.bit5
#define ID6 D_DIN.bit6
#define ID7 D_DIN.bit7

转载请注明出处。作者:四极管。广西师范大学 电子工程学院大学生科技创新基地 邮箱: yangxingbo-0311@163.com。

四极管:IIC之AVR 24c64读写相关推荐

  1. linux下at24c02驱动程序,Linux下iic(i2c)读写AT24C02

    linux内核上已有iic的驱动,因此只需要对该iic设备文件进行读写则能够控制外围的iic器件.这里以AT24C02为对象,编写一个简单的 linux内核上已有iic的驱动,因此只需要对该iic设备 ...

  2. 示波器观察IIC通讯协议-STM32F4读写24C08EEPROM时序图-新人首更

    示波器观察时序不是因为好奇,是因为遇到了问题 STM32F4探索者开发板板载24C02EEPROM,自制了一块开发板,需要存储容量更大的24C08A芯片,焊接后发现开发板上能成功运行的程序,在自己的板 ...

  3. STM32用IIC实现EEPROM的读写

    本次使用的eeprom芯片是AT24CO2,stm32芯片是103zet6. 图1.1与图1.2为电路原理图,采用PB6作为SCL,PB7作为SDL; 图1.1 电路原理图 图1.2 电路原理图 图1 ...

  4. STM32的IIC(模拟)读写AT24c02

    1.GPIO的工作模式有八种.IIC的SCL可设置为输出,但是SDA需要收发信号,所以要设置为输入和输出两种形式. #define SDA_IN() {GPIOB->CRL&=0X0FF ...

  5. AVR(Mega32)读写内部EEPROM

    开发工具:codeblocks+winAVR2010 方式一:(根据Atmega32资料)其实就两个函数--不知道为什么有时候成功又时候失败(不明所以):结合这两个读写函数,可以自己重写出其他读写一个 ...

  6. linux i2c dev.h freq,STM32F103ZET(基于秉火开发板)+Cubemx(F1 V1.60库)+IIC+AT24C02(修复官方例程读写死机bug)...

    首先说明下开发条件: 1.开发板:秉火霸道,STM32F103ZET 2.软件:Cubemx V4.23(F1 V1.60库) 3.硬件:AT24C02 256KByte 问题描述:Cubemx生成I ...

  7. STM32H7系列使用硬件IIC读写EEPROM(HAL库配置源码)

    记得在使用STM32F103系列时,好多人说其硬件IIC通讯不稳定.后来我们用到了STM32H743的单片机,使用了其硬件IIC对EEPROM进行读写.硬件IIC使用并不麻烦,而且相比于I/O模拟的I ...

  8. IIC总线的原理与Verilog实现

    IIC总线的原理与Verilog实现 1. 软件平台与硬件平台 2. 原理介绍 2.1 IIC总线的特点: 2.2 IIC总线协议详解: 2.2.1 IIC主机往从机里面写入数据的步骤 2.2.2 I ...

  9. iic总线从机仲裁_IIC协议底层原理超详细解析!示波器,逻辑分析仪多图预警

    1. 协议基础 1.1.     协议简介 IIC-BUS(Inter-IntegratedCircuit Bus)最早是由PHilip半导体(现在被NXP收购)于1982年开发.主要是用来方便微控制 ...

最新文章

  1. WhyGL:一套学习OpenGL的框架,及翻写Nehe的OpenGL教程
  2. 使用NGUINGUI的相关介绍
  3. 035 函数和代码复用小结
  4. 类模板与运算符重载(一个简单的例子)
  5. Jmeter录制app脚本
  6. 早期计算机的应用主要是( ) (2分),计算机基础第1次作业(含答案)
  7. 怎么设置html编译报错,doctype html编译出错,提示unexpected character D,这是怎么回事呀?...
  8. nginx: too many open files
  9. Vue 使用 print.js 实现打印组件
  10. Eprime error number 1234 :unable to load sound 203
  11. linux内核默认imx6速率配置,Linux4.1.15内核移植-imx6ull
  12. 3D建模软件快捷键操作:3DMAX篇(第二期)
  13. 查找代码文件中的非 ASCII 字符
  14. R语言实现关联规则与推荐算法(学习笔记)
  15. 6-3 BMI计算(类与对象) (10分)
  16. 自学网络安全,一般人我劝你放弃吧!
  17. vue之packages.json添加注释的正确写法
  18. 服务器应用安全措施_建议的安全措施来保护您的服务器
  19. 计算机在语文教学中的用场,项目教学法在计算机基础教学中的应用:项目教学 语文教学法...
  20. Android自定义控件——仿微信语音按钮

热门文章

  1. 2022年上海应届生落户政策!没有社保基数要求,能直接落户!
  2. Redis面试题 70道
  3. 思科服务器怎么看型号,通过型号快速识别思科路由器,交换机,服务器等设备
  4. jenkins编译打包及自动化部署
  5. Android IBinder机制简单介绍
  6. App三种启动场景:冷启动、热启动、温启动
  7. 在线九宫切图(九宫格切图)工具
  8. NET连接mysql字符串
  9. 软件评测师题库--程序语言基础知识
  10. wps表格户主序号_WPS表格怎么设置自动排列序号?