for index,val := range a {
目前成都创新互联已为上1000家的企业提供了网站建设、域名、网站空间、网站托管维护、企业网站设计、延津网站维护等服务,公司将坚持客户导向、应用为本的策略,正道将秉承"和谐、参与、激情"的文化,与客户和合作伙伴齐心协力一起成长,共同发展。
if val == '好' {
fmt.println(index,x)
}
}
对string做range得到的val是int32类型,直接用单引号比较就行
图例如下:
结果应该是分别是:
广度优先: a - b - c - d - f - e - g
先序遍历: a - b - d - e - f - g - c
中序遍历: e - d - b - g - f - a - c
后序遍历: e - d - g - f - b - c - a
结果存在result里面,如果不存可以少一层变量
这个地方强烈建议读一下下面的第一个链接,我遵照着那篇文章实现的,只是用Go改写了而已。
首先定义一个数据结构,用来存储一些Node的信息。
这里是可以运行的,但是总会抛出一个数组越界的错误,我看了半天也没看出来哪里有问题,Mac版的devel我这边又有bug,没用起来。至少思路对了,我后面再看一下哪里的问题。(感谢 @RiXu 指正)
2021-11-10
列表是一种非连续的存储容器,有多个节点组成,节点通过一些变量记录彼此之间的关系
单链表和双链表就是列表的两种方法。
原理:A、B、C三个人,B懂A的电话,C懂B的电话只是单方知道号码,这样就形成了一个单链表结构。
如果C把自己的号码给B,B把自己的号码给A,因为是双方都知道对方的号码,这样就形成了一个双链表结构
如果B换号码了,他需要通知AC,把自己的号码删了,这个过程就是列表的删除操作。
在Go语言中,列表使用 container/list 包来实现,内部的实现原理是双链表,列表能够高效地进行任意位置的元素插入和删除操作。
列表初始化的两种办法
列表没有给出具体的元素类型的限制,所以列表的元素可以是任意类型的,
例如给列表中放入了一个 interface{} 类型的值,取出值后,如果要将 interface{} 转换为其他类型将会发生宕机。
双链表支持从队列前方或后方插入元素,分别对应的方法是 PushFront 和 PushBack。
列表插入函数的返回值会提供一个 *list.Element 结构,这个结构记录着列表元素的值以及与其他节点之间的关系等信息,从列表中删除元素时,需要用到这个结构进行快速删除。
遍历完也能看到最后的结果
学习地址:
先来看一个简单的例子
输出的结果为:
从上面例子中可以看出,string是以byte数组形式存储的,而一个utf8格式的中文占3个byte.要得到正确的中文字符的长度和分割,可以使用 rune 数组来拆分. rune类型是int32的别名,一个rune可以表示一个中文字符,go也提供了rune数组自动拆分string中文字符的方法 rt := []rune(str) .
我们再把上面例子修改一下:
得到的输出结果为:
这样就能比较好的处理中文了,而且不会出现乱码的情况.
#include iostream
#include string.h
using namespace std;
void main()
{
char *p[3] ={"HELLO","5465465","go132HOME"}, str[100];
int i, j, k;
for(i = 0; i 3; i++)
cout p[i] endl;
cout endl;
for(i = 0; i 3; i++)
{
for(k = 0; k 100; k++) str[k] = '\0';
for(k=0;*(p[i]+k);k++)
str[k] = *(p[i]+k);
for(j = 0; str[j]; j++)
{
if(str[j] = 65 str[j] = 90) {str[j] = str[j] + 32;cout str[j];continue;}
if(str[j] = 97 str[j] = 122) {str[j] = str[j] - 32;cout str[j];continue;}
cout str[j];
}
cout endl;
}
}
又:
/*用指针数组方式定义3个字符串,然后遍历每个字符串,把里面的小写字母改大写,大些字母改小写。 */
#include iostream
#include string.h
using namespace std;
void main()
{
char *p[3] ={"HELLO","5465465","go132HOME"}, str[100];
int i, j, k;
for(i = 0; i 3; i++)
cout p[i] endl;
cout endl;
for(i = 0; i 3; i++)
{
for(k = 0; k 100; k++) str[k] = '\0';
for(k=0;*(p[i]+k);k++)
str[k] = *(p[i]+k);
for(j = 0; str[j]; j++)
{
if(str[j] = 65 str[j] = 90) {str[j] = str[j] + 32;goto flag;}
if(str[j] = 97 str[j] = 122) {str[j] = str[j] - 32;goto flag;}
flag: cout str[j];
}
cout endl;
}
}
注意:用指针数组不能直接改
即不能用 *p = *p + 32;
否则出现错误: unhandled exception 0xC0000005
对于切片的顺序遍历,一般使用 range 就可以了。
这里有一个问题需要注意一下,如果这里的切片nums不是基本数据类型而是结构体。range遍历出来的value值是拷贝值而并非原结构体,修改value中的值不会改变原切片中的值。如果要遍历修改,可以将切片的结构体改为指针,或都索引来取值。
一般情况下逆序遍历思路就是for size-1到0.
二般的也可以使用range来遍历