打印
[应用方案]

单片机C语言教程之字符串指针

[复制链接]
1306|1
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
Jessicakjdsl|  楼主 | 2016-4-20 22:33 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
c语言中,引号分为单引号和双引号。双引号里面的是字符串,而单引号里面代表字符。单引号和双引号的区别:
1)单引号引起的一个字符代表一个整数,整数值对应于该字符在ASCII字符集中的序列值;双引号引起的都是字符串,哪怕只有一个字符也是字符串,双引号引起的一个字符代表一个指向无名数组起始字符的指针。
比如: ‘.’代表十进制46,十六进制0x2e;
而”.”代表指向起始字符为”.”的某数组的指针;
2)大小不同
单引号引起的一个字符大小就是一个字节;
双引号引起的一个字符大小是两个字节,因为双引号引起的字符串会在字符串的末尾添加一个0x00作为字符串的结束标识。
在C语言中,可以用两种方法访问一个字符串。
1)用字符数组存放一个字符串,然后输出该字符串

char string[]=”I love China!”;

说明:和前面介绍的数组属性一样,string是数组名,它代表字符数组的首地址。
2)用字符串指针指向一个字符串

char *string =”goodday”
字符串指针变量的定义说明与指向字符变量的指针变量说明是相同的。只能按对指针变量的赋值不同来区别。对指向字符变量的指针变量应赋予该字符变量的地址。如

char c, *p=&c;

表示p是一个指向字符变量c的指针变量。
而:

char *s = “C language”;

则表示s是一个指向字符串的指针变量。把字符串的首地址赋予s

上例中,首先定义string是一个字符指针变量,然后把字符串的首地址赋予string(应写出整个字符串,以便编译系统把该串装入连续的一块内存单元),并把首地址送入string. 程序中的:

char *ps=”C langage”;

等效于:

char *ps;
ps=”C Language”;

在打印字符的时候,为什么是mystring而不是*mystring,mystring不是表示一个地址吗?
这个就涉及到%s的用法了。%s要求输入一个指针,或数组名,表示的是一个地址;如果换成printf(%d%c)等等,就需要使用指针指向的变量了。

/*目的:用两种方式来访问字符串
1. 数组的形式       char string[]="Hello, world!"
2. 字符指针的形式   char *string="hello, world!"
*/
#include "stdio.h"
char mystring1[] = "Hello,world!";
char *mystring2 = "hello, world!";
void main(void)
{
    printf("%s\n",mystring2);
    printf("%s\n",mystring1);
    system("pause");
}

现在来看看如何在单片机编程中使用。前面我们在做LCD1602的实验中,实现了单个字符写入1602中,那么如何写一个字符串呢?这里我们使用指针变量作为函数参数,把要写入的字符串地址传递给函数,然后通过write_data()函数一个一个写入。

void write_string(unsigned char *p)
{
        write_data(*p);
}

沙发
Jessicakjdsl|  楼主 | 2016-4-20 22:33 | 只看该作者
假设要写入的字符串为”Anystring”,那么以上代码中写入的是A, 如果要继续写入’n’,需要让p+1,重复以上步骤就可以将整个字符串写完。现在的问题是如何判断字符串有多少个字符呢?也就是说p=p+1要执行多少次呢?前面讲了,字符串有个0x00的结束标志符。因此这里我们可以用while(*p)循环,当p自增时,字符串写完后*p为0,跳出while循环。代码如下:
#include "reg52.h"
sbit RS=P2^7;
sbit EN=P2^6;
void LCD_init(void);
void delayUs(unsigned char t);
void delayMs(unsigned char t);
void write_com(unsigned char mycmd);
void write_data(unsigned char mydata);
void write_string(unsigned char *p);

void main(void)
{
    LCD_init();        
    write_com(0x0f);
//  write_data(0x41);
    write_string("Any String");
    while(1);
}


void LCD_init(void)
{
    delayMs(15);
    write_com(0x38);
    delayMs(5);
    write_com(0x38);
    write_com(0x08);
    write_com(0x01);
    write_com(0x06);
    write_com(0x0c);
}

void write_data(unsigned char mydata)
{
  delayMs(5);//注意这里需要延时5ms比较保险
  P0=mydata;
  RS=1;
  EN=1;
  delayUs(5);
  EN=0;
}

void write_string(unsigned char *p) //如何写一个字符串
{
    while(*p)
    {
        write_data(*p);
        p++;
    }
}

void write_com(unsigned char mycmd)
{
  delayMs(5);//注意这里需要延时5ms比较保险 代替判断忙信号
  P0=mycmd;        //准备好指令
  RS=0;         //告诉LCD1602,P0中放的是指令不是数据
  EN=1;
  delayUs(5); //根据时序图,脉冲要有一定宽度
  EN=0;           //使指令有效,开始执行
}  

void delayUs(unsigned char t)
{
        while(--t);
}

void delayMs(unsigned char t)
{
        while(--t)
        {
                delayUs(245);
                delayUs(245);
        }
}


使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

17

主题

116

帖子

1

粉丝