30天学会C语言: Day 10-你的字串不是字串

字元

电脑中的字元其实是由整数数字表示,就像是每一个字元都有一个属於自己的编号,

printf() 可以查看代表字元的整数

#include<stdio.h>
#include<stdlib.h>

int main(){
	printf("%d %d\n", '0', '9');
	printf("%d %d\n", 'A', 'Z');
	printf("%d %d\n", 'a', 'z');
	
	return 0;
}

字元 0 ~ 9, A ~ Za ~ z 的数值是连号而且由小到大
大小写和小写字母相差42

利用这些性质,可以用来对字串进行一些操作

C语言中的字串

在C语言中,并没有 String 这个型别,而是用字元的阵列 (character Array) 作为字串

在C语言中,空字元('\0')代表字串结束
所以 "123",其实是一个长度为四的一维字元阵列,它的元依序是 '1', '2', '3', '\0'

宣告

就和宣告阵列一样,但因为阵列的大小上限在宣告的时候就决定了,所以宣告时要注意输入的大小

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100];
	
	return 0;
}

可以用和阵列一样的方法初始化字串的内容

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100]={'H', 'e', 'l', 'l', 'o', '!', '\0'};
	
	return 0;
}

或是用双引号代表字串,但一样只能在宣告时用这个方法指派

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100]="Hello!";
	
	return 0;
}

输出

printf()

字串的预留位置用 %s 表示

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100]="PJ";
	printf("My name is %s.", s);
	return 0;
}

如果只要显示字串中的内容,可以直接把字串作为 printf() 的引数

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100]="Hello!";
	printf(s);
	return 0;
}

puts()

puts() 函式的引数为一个字串,功能是将引数显示到萤幕上,会自动在字串结尾换行,但没有格式化字串的功能(无法显示其他型别的资料)

#include<stdio.h>
#include<stdlib.h>

int main(){
	puts("1");
	puts("2");
	return 0;
}

显示字串变数

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[10]="Hello!";
	puts(s);
	return 0;
}

输入

scanf()

因为阵列实际上就是指标,所以字串变数前面不用 &
宣告时设定的阵列长度,要比输入的字串还长,下面例子中的 name 最大可以储存99个字元(99个字元加上一个'\0')

#include<stdio.h>
#include<stdlib.h>

int main(){
	char name[100];
	scanf("%s", name);
	printf("My name is %s.\n", name);
	
	return 0;
}

如果使用的预留位置是 %sscanf() 遇到空格就会以为是另一个数值,字串会不完整

如果输入的字串 包含空格 必须用 %[^\n]

#include<stdio.h>
#include<stdlib.h>

int main(){
	char name[100];
	scanf("%[^\n]", name);
	printf("My name is %s.\n", name);
	
	return 0;
}

常见字串处理

字串长度

指从头开始到空字元 '\0' 前的字元数量(不包含'\0')

可以用回圈计算字串长度,或是透过函式库 string.h 中的函式取得

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100]="Hello!";
	int len=0;
	for(int i=0; s[i]!='\0'; i++)
		len++;
	printf("%d\n", len);
	return 0;
}

除了先用一个回圈计算字串长度,也常常直接把字串处理的内容写在回圈中

大小写/英数 判断

因为字元实际上是整数,所以可以用来进行比较运算
结合比较运算和逻辑运算,可以判断某字元是数字、大写字母或小写字母

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100];
	scanf("%s", s);
	for(int i=0; s[i]!='\0'; i++){
		if(s[i]>='a' && s[i]<='z')
			printf("%c is a lowercase letter.\n", s[i]);
		else if(s[i]>='A' && s[i]<='Z')
			printf("%c is a capital letter.\n", s[i]);		
		else if(s[i]>='0' && s[i]<='9')
			printf("%c is a numerical digit.\n", s[i]);
	}
	return 0;
}

大小写转换

因为字元实际上是整数,所以可以做数学运算
因为大写和小写相差42,所以可以透过加减42达成大小写转换

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100];
	scanf("%s", s);
	for(int i=0; s[i]!='\0'; i++){
		if(s[i]>='a' && s[i]<='z')
			s[i]-=42;
		else if(s[i]>='A' && s[i]<='Z')
			s[i]+=42;
	}
	return 0;
}

或是加上 'A''a' 之间的差

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100];
	scanf("%s", s);
	for(int i=0; s[i]!='\0'; i++){
		if(s[i]>='a' && s[i]<='z')
			s[i]+=('A'-'a');
		else if(s[i]>='A' && s[i]<='Z')
			s[i]+=('a'-'A');
	}
	printf("%s\n", s);
	return 0;
}

偏移(凯萨加密)

例如将字串中的 'a' 变成 'b''b' 变成 'c'...'z' 变成 'a' 这类的题目,可以透过数学运算完成
因为 'z' 加上1不会变成 'a',所以要用 if() 另外处理

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100];
	scanf("%s", s);
	for(int i=0; s[i]!='\0'; i++){
		if(s[i]>='a' && s[i]<='z'){
			s[i]+=1;
			if(s[i]>'z')
				s[i]='a';
		}
	}
	printf("%s\n", s);
	return 0;
}

或是透过数学运算

#include<stdio.h>
#include<stdlib.h>

int main(){
	char s[100];
	scanf("%s", s);
	for(int i=0; s[i]!='\0'; i++){
		if(s[i]>='a' && s[i]<='z'){
			s[i]=s[i]-'a'+1;
			s[i]%=26;
			s[i]+='a';
		}
	}
	printf("%s\n", s);
	return 0;
}


挖坑清单:

  • main() 前面的 int,和最後一行的 return 0;
  • 可以拆成多行的情况
  • 指标

<<:  UML 图摘要

>>:  30天学会 Python: Day 10-读进来!写出去!

时间挤一下就有了,我们挤了没?

前言 利用前几天的篇幅,简单的讨论敏捷与 Scrum,也传达了我觉得团队需要注意的地方。今天再让我们...

Elastic Stack第二十九重

Logstash 本篇介绍何谓Logstash以及他的功用,并从安装到使用基本的pipeline L...

给自己学习30天重新认识css

哈罗大家好,我是黄奇昌 我就读岭东科技大学视觉传达设计系 今年是第一次参加13th铁人赛,想跟大家好...

Day#13 登入画面(2)

前言 昨天成功的放上imageView以及标题,今天来把其他的栏位放上~ 登入栏位 LoginVie...

SQL Server 系统资料库的介绍

DBABootcamp SQL Server 主要的系统资料库有以下 4 种。 — master 资...