Golang学习笔记魂士篇MTIT

编译语言:需要解释器,比如jvm,解释称二进制,然后处理器才能执行解释性:编译后为二进制语言

C、C++、Python、PHP/java/javascript等都是2005之前的,2005年出现了多核处理器,go在2007年出现,go天生支持并发

go语言特点:

应用范围:

腾讯内部go语言:蓝鲸、微服务架构TarsGo、云平台

知乎go语言重构

docker,k8s

...

Go语言使用场景:

go语言规定src,pkg,bin...目录统称为工作区,其中src目录必须手动创建,

如果是vscode安装,安装插件(1、chinses(中文),2、go安装)

注意:在哪个目录下执行gobuildmain.go,在哪个录下生成main.exe

gobuild-ohello.exe默认编译当前目录

goinstall安装

1、编译得到一个可执行文件2、拷贝到GOATH/bin1.2、跨平台编译main函数是程序的入口文件函数外(不在func内)只能放置标识符(变量、常量、)

默认我们gobuild的可执行文件都是当前操作系统可执行的文件,如果我想在windows下编译一个linux下可执行文件,那需要怎么做呢?

只需要指定目标操作系统的平台和处理器架构即可:

SETCGO_ENABLED=0//禁用CGOSETGOOS=linux//目标平台是linuxSETGOARCH=amd64//目标处理器架构是amd64使用了cgo的代码是不支持跨平台编译的

然后再执行gobuild命令,得到的就是能够在Linux平台运行的可执行文件了。

Mac下编译Linux和Windows平台64位可执行程序:

CGO_ENABLED=0GOOS=linuxGOARCH=amd64gobuildCGO_ENABLED=0GOOS=windowsGOARCH=amd64gobuildLinux下编译Mac和Windows平台64位可执行程序:

CGO_ENABLED=0GOOS=darwinGOARCH=amd64gobuildCGO_ENABLED=0GOOS=windowsGOARCH=amd64gobuildWindows下编译Mac平台64位可执行程序:

SETCGO_ENABLED=0SETGOOS=darwinSETGOARCH=amd64gobuild现在,开启你的Go语言学习之旅吧。人生苦短,let’sGo.

注意:在目录内执行gobuild,会生成一个不带exe,文件名为目录名的二进制可执行文件

Go1.14版本之后,都推荐使用gomod模式来管理依赖环境了,也不再强制我们把代码必须写在GOPATH下面的src目录了,你可以在你电脑的任意位置编写go代码。(网上有些教程适用于1.11版本之前。)

可以执行下面的命令修改GOPROXY:

创建目录:D:\Program_language\PRD\PG1并添加系统环境变量:GOPATH=D:\Program_language\PRD\PG1GOBIN=D:\Program_language\PRD\bin1.4、liteIde快捷键ctrl+{|}#快速到函数头部或尾部ctrl+/#选中范围进行注释ctrl+shift+i#鼠标放在对应的函数上,提示函数参数信息ctrl+alt+i#代码格式化二、数据类型2.1、变量和常量标识符:(程序中具有特殊意义的词,比如常量名、变量名、函数名等)标识符命名规范:字母、数字、下划线,只能以字母和下划线开头

25个关键字:

breakdefaultfuncinterfaceselectcasedefergomapstructchanelsegotopackageswitchconstfallthroughifrangetypecontinueforimportreturnvar37个保留字:

Constants:truefalseiotanilTypes:intint8int16int32int64uintuint8uint16uint32uint64uintptrfloat32float64complex128complex64boolbyterunestringerrorFunctions:makelencapnewappendcopyclosedeletecomplexrealimagpanicrecover变量的来历:程序运行过程中的数据是放在内存中的,利用变量在保存内存地址,使用方便

变量的类型:go语言中每个变量都有属于自己的类型,并且变量必须初始化后才能被使用

变量初始化:

常量:

注释://单行注释

/*多行注释*/变量交换

funcmain(){ stu1,stu2:=10,20 fmt.Println(stu1,stu2) //1、变量交换 stu1=stu2 fmt.Println(stu1,stu2)//2020结果 stu2=stu1 fmt.Println(stu1,stu2)//2020结果 //2、变量交换-中间变量 stu1,stu2=10,20 fmt.Println(stu1,stu2)//1020 c:=stu1 stu1=stu2 stu2=c fmt.Println(stu1,stu2)//2010 //2、变量交换-方式3 stu1,stu2=10,20 stu1,stu2=stu2,stu1 fmt.Println(stu1,stu2)//2010}2.2、iotaiota是go的常量计数器,只能在常量的表达式中使用

const( a=100 b=200 c=iota) fmt.Println(a,b,c)//100,200,2 const( d=iota e=100 f=iota ) fmt.Println(d,e,f)//0,100,2 const( m1,m2=iota+1,iota+2//iota为0 m3,m4=iota+1,iota+2//iota为1 ) fmt.Println(m1,m2,m3,m4)//1,2,2,3 const( _=iota KB=1<<(10*iota)//iotao为1,1左移10位 MB=1<<(10*iota) GB=1<<(10*iota) TB=1<<(10*iota) PB=1<<(10*iota) ) fmt.Println(KB,MB,GB,TB,PB) /* 10241048576107374182410995116277761125899906842624 */容量单位:

整形:

其他数字类型:

浮点型和复数:

v:=0b00101101,代表二进制的101101,相当于十进制的45。v:=0o377,代表八进制的377,相当于十进制的255。v:=0x1p-2,代表十六进制的1除以22,也就是0.25。而且还允许我们用_来分隔数字,比如说:

v:=123_456等于123456。

packagemainimport"fmt"funcmain(){ //十进制 varaint=10 fmt.Printf("%d\n",a)//10 fmt.Printf("%b\n",a)//1010占位符%b表示二进制 //八进制以0o开头 varbint=077 fmt.Printf("%o\n",b)//77 //十六进制以0x开头 varcint=0xff fmt.Printf("%x\n",c)//ff fmt.Printf("%X\n",c)//FF}2.6、八进制&十进制go语言中无法直接定义二进制

funcstr(){ path1:="D:\\Golang\\project\\project1\\src" path2:=`D:\Golang\project\project1\src`//path1和path2效果一样 issue:=`床前明月光疑是地上霜举头望明月低头思故乡` fmt.Println(path1) fmt.Println(path2) fmt.Println(issue)}字符串的常用操作

funcstr2(){a1:="hello"a2:="world"//info:=a1+a2拼接方法1//fmt.Println(info)fmt.Printf("%s%s",a1,a2)ss1:=fmt.Sprintf("%s%s",a1,a2)//拼接方法2,返回结果为一个字符串fmt.Println(ss1)//分割ret:=strings.Split(ss1,"o")//以"o"为分隔符[hellwrld]fmt.Println(ret)//拼接fmt.Println(strings.Join(ret,"+"))//hell+w+rld//包含判断fmt.Println(strings.Contains(ss1,"world"))//truefmt.Println(strings.Contains(ss1,"Hello"))//false//前缀,后缀fmt.Println(strings.HasPrefix(ss1,"hello"))//truefmt.Println(strings.HasSuffix(ss1,"hello")) //falsess2:="aboddbc2oa"//子串出现的位置fmt.Println(strings.Index(ss2,"o"))//2fmt.Println(strings.LastIndex(ss2,"o"))//8}修改字符串

字符串:不可变类型修改字符串,需要先将其转换成[]rune,或者[]byte,完成后在转换string,无论哪种转换,都会重新分配内存。无论哪种转换,都会重新分配内存,并复制字节数组。

其他类型转换成字符串

funcstr1(){ str:="helloworld" slice:=[]byte(str) fmt.Println(slice)//[10410110810811132119111114108100]} funcstr2(){ str:=[]byte{'h','e','l','l','0',97} fmt.Println(str)//[1041011081084897] fmt.Println(string(str))//hell0a}funcstr3(){//将其他类型转换为字符串format系列函数 str:=strconv.FormatInt(120,8) fmt.Println(str)//170,120转换成8禁止120%8=15余0;15%8=1余7 //funcFormatFloat(ffloat64,fmtbyte,prec,bitSizeint)string//fmt打印方式,prec:小数位保留个数,bitSize:float32还是float64 s2:=3.1415926 s3:=strconv.FormatFloat(s2,'f',4,32) fmt.Printf("%T\t%v\n",s3,s3)//string 3.1416}字符串转换为其他类型

funcstr4(){ a,b,c:="3.14","true","12" fmt.Printf("%T\t%T\t%T\n",a,b,c)//string string string a1,err:=strconv.ParseInt(a,10,32)//转换为int;数字是什么进制表示的,要存储为int32/int64 iferr!=nil{ fmt.Println(err)//parsing"3.14":invalidsyntax } a2,_:=strconv.ParseFloat(a,32)///期望的接受类型为float32,具体以实际为准 a3,err:=strconv.ParseInt(c,16,32)//c"12"为16进制,转换为int32 b1,_:=strconv.ParseBool(b) fmt.Printf("%T\t%T\t%T\t%T\n",a1,a2,a3,b1)//int64 float64 int64 bool fmt.Println(a1,a2,a3,b1)//03.1418true}其他类型字符串

vara:='中'varb:='x'Go语言的字符有以下两种:

当需要处理中文、日文或者其他复合字符时,则需要用到rune类型。rune类型实际是一个int32。

Go使用了特殊的rune类型来处理Unicode,让基于Unicode的文本处理更为方便,也可以使用byte型进行默认字符串处理,性能和扩展性都有照顾。

//遍历字符串functraversalString(){ s:="hello沙河" fori:=0;i

104(h)101(e)108(l)108(l)111(o)230()178(2)153()230()178(2)179(3)104(h)101(e)108(l)108(l)111(o)27801(沙)27827(河)因为UTF8编码下一个中文汉字由3~4个字节组成,所以我们不能简单的按照字节去遍历一个包含中文的字符串,否则就会出现上面输出中第一行的结果。

字符串底层是一个byte数组,所以可以和[]byte类型相互转换。字符串是不能修改的字符串是由byte字节组成,所以字符串的长度是byte字节的长度。rune类型用来表示utf8字符,一个rune字符由一个或多个byte组成。

程序的三大结构:顺序结构、选择结构、循环结构

用法

ifcondition{//单条件判断//dosomething}ifcondition{//多条件判断}elseifcondition{//dosomething}else{//dosomething}if单条件先跟个语句然后再做条件判断

ifstatement;condition{//单条件,带语句的判断//dosomething}funcmain(){////多条件,不带语句的判断 ifnum:=34,num<=50{//num的作用域只在if语句内有效 fmt.Println("Numberislessthen50") }elseifnum>=51&&num<=100{ fmt.Println("Thenumberisbetween51and1100") }else{ fmt.Println("Thenumberisgreaterthan100") } fmt.Println(num)//会失败,因为num的作用域只在if范围内有效}3.2、forgo只有for没有while循环for循环可以通过break,goto,return,panic语句强制退出循环go语言中forrange遍历数组、切片、字符串、map以及通道(channel)。通过forrange遍历的返回值有一下规律:1、数组、切片、字符串返回索引和值2、map返回键和值3、通道只返回通道内的值for初始语句;条件表达式;结束语句{//格式1循环体}for;条件表达式;结束语句{//格式2循环体}for条件表达式{//格式3循环体}for{//格式4,死循环循环体语句}示例1

funcstr6(){ info:="hello中国" fori,v:=rangeinfo{ //fmt.Println(i,v)//默认输出的是utf-8的编自值 fmt.Printf("%v%s\n",i,string(v)) //fmt.Printf("%d%c\n",i,v)//效果同上,打印字符 }}示例2

funcbreak1(){ fori:=0;i<10;i++{ ifi==3{ continue//跳过本次循环 } ifi==5{ break//跳出for循环 } fmt.Println(i) } fmt.Println("over")}99乘法表

funca99(){ fori:=1;i<=9;i++{ forv:=1;v<=i;v++{ fmt.Printf("%d*%d=%v\t",i,v,i*v) } fmt.Println() }}3.3、switch简化大量的判断和一个具体的值进行判断

funcgoDemo1(){ varbreakFlagbool fori:=0;i<10;i++{ forv:=0;v<=10;v++{ ifv==3{ breakFlag=true break//1个break只跳出一层循环 } fmt.Println(i,v) } ifbreakFlag{//如果breakFlag为ture,就跳出外层循环 break } }}funcgoDemo2(){//优化后的go代码 fori:=0;i<10;i++{ forv:=0;v<=10;v++{ ifv==3{ gotobreakFlag//跳转到指定label } fmt.Println(i,v) } }breakFlag://label名称 fmt.Println("GameOver...!")}3.5、break和continue跳转语句:go和breakbreak语句可以结束for、switch和select的代码块。

break语句还可以在语句后面添加标签,表示退出某个标签对应的代码块,标签要求必须定义在对应的for、switch和select的代码块上。举个例子:

funcbreakDemo1(){BREAKDEMO1: fori:=0;i<10;i++{ forj:=0;j<10;j++{ ifj==2{ breakBREAKDEMO1 } fmt.Printf("%v-%v\n",i,j) } } fmt.Println("...")}continue语句可以结束当前循环,开始下一次的循环迭代过程,仅限在for循环内使用。

在continue语句后添加标签时,表示继续执行开始标签对应的循环的下一次循环。例如:

#1、不加labelfuncmain(){ forx:=1;x<=9;x++{ fory:=x;y<=9;y++{ ify==2{ continue } fmt.Printf("%d*%d=%d\t",x,y,x*y) } fmt.Println() }}D:\Program_language\PRD\PG1\src>gorunmain.go1*1=11*3=31*4=41*5=51*6=61*7=71*8=81*9=92*3=62*4=82*5=102*6=122*7=142*8=162*9=183*3=93*4=123*5=153*6=183*7=213*8=243*9=274*4=164*5=204*6=244*7=284*8=324*9=365*5=255*6=305*7=355*8=405*9=456*6=366*7=426*8=486*9=547*7=497*8=567*9=638*8=648*9=729*9=81#2、加上labelfuncmain(){test: forx:=1;x<=9;x++{ fory:=x;y<=9;y++{ ify==2{ continuetest } fmt.Printf("%d*%d=%d\t",x,y,x*y) } fmt.Println() }}D:\Program_language\PRD\PG1\src>gorunmain.go#continue到外层循环1*1=13*3=93*4=123*5=153*6=183*7=213*8=243*9=274*4=164*5=204*6=244*7=284*8=324*9=365*5=255*6=305*7=355*8=405*9=456*6=366*7=426*8=486*9=547*7=497*8=567*9=638*8=648*9=729*9=81四、高级数据类型4.1、运算符go语言内置的运算符:

位运算符:

定义数组

初始化

注意:多维数组只有第一层可以使用...来让编译器推导数组长度。例如:

packagemainimport( "fmt" "math/rand" "time")/*1、定义const,确定取值范围2、定义每个const的随机取值3、随机在每个const中取出随机的值*/const( NUmStr="0123456789" CharStr="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz" SpecStr="+=-@#~,.[]()!%^*$")funcranSecret(nint){ rand.Seed(time.Now().UnixNano()) varranS=func()int{ returnrand.Intn(3) } varranNum=func()string{ returnstring(NUmStr[rand.Intn(len(NUmStr))]) } varranChart=func()string{ returnstring(CharStr[rand.Intn(len(CharStr))]) } varranSpec=func()string{ returnstring(SpecStr[rand.Intn(len(SpecStr))]) } //varsecret[n]string//non-constantarraybound,go数组的长度必须是常量,不能是变量 secret:=make([]string,n) fori:=0;i

切片的三要素:指针、长度、容量//指针:切片第一个元素

切片不能直接比较,切片唯一合法的比较操作是:nil一个nil值的切片并没有底层数组,一个nil值的切片的长度和容量都是0。但是我们不能说一个长度和容量都是0的切片一定是nil,例如下面的示例:

一个nil的底层切片是切片是没有底层数组的,长度和容量都是0。但我们不能说长度和容量都是0的切片一定是nil(len(s)==0和s==nil是不一样的)

切片的扩容策略:

funccopy1(){//copy目标slice未初始化,会copy失败,但是不会报错 a1:=[]int{1,2,3} a2:=a1 a2[0]=100 vara3[]int copy(a3,a1) fmt.Println(a1)//[10023] fmt.Println(a2)//[10023] fmt.Println(a3==nil)//true fmt.Println(a3)//[]因为a3是nil,需要对a3初始化后才能使用。}funccopy2(){//copy目标slice初始化但是len为0,仍会copy失败 a1:=[]int{1,2,3} a2:=a1 a2[0]=100 vara3[]int a3=make([]int,0,3) copy(a3,a1) fmt.Println(a1)//[10023] fmt.Println(a2)//[10023] fmt.Println(a3==nil)//false fmt.Println(a3)//[],copy不会自动扩容切片,而a3的长度为0,因此拷贝不进去结果为[]}funccopy3(){ a1:=[]int{1,2,3} a2:=a1 vara3[]int a3=make([]int,3,3) copy(a3,a1) a2[0]=100 fmt.Println(a1)//[10023] fmt.Println(a2)//[10023] fmt.Println(a3==nil)//false fmt.Println(a3)//[123]}4.3.2、切片传递数组参数传递为值传递,切片是引用传递,在被调函数内修改会修改原有切片值

funcslice4(a[]int){ a[0]=100//这里修改的是原slice的 a=append(a,4,5,6) a[0]=200 fmt.Println(a)//[2002345456],这里不会修改原slice,因为slice进行了扩容,开辟了新的内存地址}funcmain(){ slice:=[]in{1,2,3,4,5} slice4(slice)//传递的是地址,切片名本身就是地址 fmt.Println(slice)//[1002345]}4.3.3、make和newmake也是用来分配内存的,区别于new,他只用于slice、map以及chan的内存创建。而且它返回的类型就是这三个类型本身,而不是他们的指针类型,因为这三种就是引用类型,所以他们没有必要返回他们的指针了。make函数的函数签名如下:funcmake(tType,size...IntegerType)Typemake函数是无可替代的,我们在使用slice、map和channel的时候。都需要使用make进行初始化,然后才可以对他们进行

make和new的区分:

代码示例1:会panic

funcmk(){ vara*int//nil *a=100//*a根据nil的内存地址找值,自然找不到 fmt.Println(a)//invalidmemoryaddressornilpointerdereference varbmap[string]int b["洛阳"]=379 fmt.Println(b)//panic:assignmenttoentryinnilmap}funcmk(){ vara1*int fmt.Println(a1)//nil vara2=new(int) fmt.Println(a2)//0xc0000100c0 fmt.Println(*a2)//0 *a2=100 fmt.Println(*a2)//100 varb=make(map[string]int,5) b["洛阳"]=379 fmt.Println(b)}4.4、指针(重点)4.4.1、指针参数传递涉及两个概念:值(存储在内存中的数据)和地址(数据所在内存的地址)

go语言不存在指针操作(不能修改),只需要记住2个字符:1、&取出地址;2、*根据地址取值

funcmap1(){ varm1map[string]int fmt.Println(m1==nil)//true,map为引用类型,需要先使用make进行初始化 m1["小明"]=18//panic:assignmenttoentryinnilmap fmt.Println(m1)}funcmap1(){ varm1map[string]int fmt.Println(m1==nil)//true m1=make(map[string]int,5)//容量建议规划合理,避免需要多次扩容 fmt.Println(m1==nil)//false m1["小明"]=18 fmt.Println(m1)//map[小明:18] delete(m1,"小刚刚")//如果删除了一个不存在的,则什么都不会做 fmt.Println(m1["小刚刚"])//如果不存在,范围0或者空 v,ok:=m1["小刚"]//判断值是否存在 if!ok{ fmt.Println("小刚不存在") }else{ fmt.Println(v) }}godocbuiltin.delete

funcs2(){ a1:="fuck" a2:="dad" a3:="abc" a4:="Geook" fmt.Println(a1,a2,a3,a4) vars1=make([]string,10) s1=append(s1,a1) s1=append(s1,a2) fork,v:=ranges1{ fmt.Println(k,v)//10fuck 11dad(0-9为s1的初始化大小),[]string在go中存储为key-value形式([int]string数组) } fmt.Println(s1[10])//fuck fmt.Println(s1[11]) //dad}//根据key名称进行排序funcrand01(){ rand.Seed(time.Now().UnixNano())//初始化随机种子 varscoreMpa=make(map[string]int,200) fori:=0;i<100;i++{ key:=fmt.Sprintf("stu%02d",i)//生成stu开头的字符串 value:=rand.Intn(100)//生成0-99的随机整数 scoreMpa[key]=value } //取出map中所有的key放到切片keys中 varkeys=make([]string,200) forkey:=rangescoreMpa{ keys=append(keys,key) } sort.Strings(keys)//对字符型切片进行排序 for_,key:=rangekeys{ fmt.Println(key,scoreMpa[key]) }}map和slice组合:

funcmap2(){ //1、元素类型为map的切片 vars1=make([]map[int]string,0,10)//对切片进行初始化,注意map并没有初始化,s1[0]表示的是s1切片的第一个元素(元素类型为map) fmt.Println(s1[0]==nil)//true s1[0][100]="A" fmt.Println(s1)//runtimeerror:indexoutofrange,因为s1的第0个元素是没有的 }funcmap2(){ //1、元素类型为map的切片 vars1=make([]map[int]string,10,10) fmt.Println(s1[0]==nil)//true s1[0]=make(map[int]string,1)//对s1[0]初始化 fmt.Println(s1[0]==nil)//false s1[0][100]="A" fmt.Println(s1)//[map[100:A]map[]map[]map[]map[]map[]map[]map[]map[]map[]] //2、值为切片类型的map varm1=make(map[string][]int,10) m1["北京"]=[]int{10,20,30} m1["上海"]=[]int{11,21,31} fmt.Println(m1)//map[北京:[102030]上海:[112131]]}练习题1:统计中文字符个数:

funccount1(){//统计中文个数 info:="Hello中国我爱你!" //1、依次获取到字符串的值 sum:=0; for_,v:=rangeinfo{ //2、判断当前这个字符是不是汉字 ifunicode.Is(unicode.Han,v){ //3、统计和输出汉字 sum++ } } fmt.Printf("infois:%v\nnumof中文字符:%d\n",info,sum)}练习题2:统计单词出现的次数:

funccount2(){//统计"howdoyoudo!"单词出现个数//1、字符串按照空格切割得到切片。2、遍历切片存储到一个map。3、累加出现的次数 info:="howdoyoudo" m1:=strings.Split(info,"")//按照空格切割为一个切片 map1:=make(map[string]int,10) for_,v:=rangem1{ map1[v]++ } fori,k:=rangemap1{ fmt.Printf("Word:\"%v\",appear%dtimes.\n",i,k) }}funccount3(){ info:="howdoyoudo" m1:=strings.Split(info,"") map1:=make(map[string]int,10) for_,v:=rangem1{ //如果原来map中不存在w这个key那么出现次数为=1 if_,ok:=map1[v];!ok{ map1[v]=1 }else{ map1[v]++ } } fori,k:=rangemap1{ fmt.Printf("Word:\"%v\",appear%dtimes.\n",i,k) }}练习题3:回文判断:

主函数作为程序的入口,是不允许有参数的

funcjiecheng(nuint8)uint8{ ifn<=1{ return1 } returnn*jiecheng(n-1)}funcmain(){ ret:=jiecheng(5) fmt.Println(ret)}n个台阶,一次可以走1步,也可以走2步,有多少种走法。

funcf11(ffunc()){//自己的 fmt.Println("thisisf11") f()}funcf22(x,yint){//别人的 fmt.Println("thisisf22") fmt.Println(x+y)}funcf33(x,yint)func(){ tmp:=func(){ fmt.Println(x,y) } returntmp}funcmain(){ //1、调用方法1 test:=f33(10,20) f11(test)//thisisf11;1020 //2、调用方法2 f11(f33(10,20))//结果同上}练习2:文件名添加后缀

//思路1,每一个jpg,txt定义一个函数,这样就比较累赘//思路2,使用闭包,返回一个函数funcmakeSuffix(suffixstring)func(filestring)string{//入参为后缀(string),出参为函数 tmp:=func(filestring)string{//定义"func(filestring)string"返回函数 if!strings.HasSuffix(file,suffix){ returnfile+suffix }else{ returnfile } } returntmp}funcmain(){ jpgFunc:=makeSuffix(".jpg")//创建jpg函数 txtFunc:=makeSuffix(".txt")//创建txt函数 fmt.Println(jpgFunc("test")) fmt.Println(jpgFunc("test.jpg")) fmt.Println(txtFunc("test"))}练习3

funcBase(baseint)(func(int)int,func(int)int){ add:=func(xint)int{ base+=x returnbase } sub:=func(yint)int{ base-=y returnbase } returnadd,sub}funcmain(){ f1,f2:=Base(10) fmt.Println(f1(1),f2(2))//11(10+1),9(11-2),调用f1(1)和f2(2)修改的都是公用的base,因此会影响。每一次只有在用到的时候才会去获取外部变量base的值 fmt.Println(f1(3),f2(4))//12(9+3),8(12-4)}5.4、fmt标准库fmt包实现了类似C语言printf和scanf的格式化I/O。主要分为向外输出内容和获取输入内容两大部分。通用占位符:

布尔型:

浮点数和复数:

字符串和[]byte:

宽度标识符:

其他flag:

Print

查找字符串/Index

funcmain(){ //1、包含-regexp.matchString str1:="helloworldworld!helloworld" match,_:=regexp.MatchString("he(..)o",str1) fmt.Println(match)//true //2、1的增强版,regexp.Compie/regexp.matchString r,_:=regexp.Compile("he(..)o") fmt.Println(r.MatchString(str1))//true;str1中是否包含"he(..)o"结果为true //3、返回匹配的子串-输出首次匹配结果/索引;r.FindString|r.FindStringIndex tmp:=r.FindString(str1) fmt.Println(tmp)//返回子串,hello fmt.Println(string(r.Find([]byte(str1))))//hello,同上 //4、返回所有匹配的字串-r.FindAllString//FindAllString和FindAllStringSubmatch用的多 str2:="abccdefghacmaskanswerprequest" r2,_:=regexp.Compile("a.") tmp2:=r2.FindAllString(str2,-1) fmt.Println(tmp2)//[abacasan] tmp3:=r2.FindAllStringSubmatch(str2,-1) fmt.Println(tmp3)//[[ab][ac][as][an]] tmp4:=r2.FindAllSubmatch([]byte(str2),-1) fmt.Println(tmp4)//[[[9798]][[9799]][[97115]][[97110]]]}替换

funcmain(){ str:="1,2,3,4,5" tmp:=strings.Split(str,",") fmt.Println(tmp)//[12345] tmp=strings.SplitAfter(str,",") fmt.Println(tmp)//[1,2,3,4,5] tmp=strings.SplitAfterN(str,",",3) fmt.Println(tmp,len(tmp))//[1,2,3,4,5]3;对'1,'和'2,'进行了切分,后面的是一块}

THE END
1.全国农业食品标准公共服务平台畜牧类 食品类 环境保护类 化妆品类 其他类 农业农村部 国家粮食局 国家发展和改革委员会 国家市场监督管理总局 国家药品监督管理局 国务院 生态环境部 国家药典委员会 商务部 工业和信息化部 国家卫生健康委员会 海关总署 国家出入境检验检疫局 国家标准化管理委员会 ...https://www.sdtdata.com/fx/fmoa/statuteLib
2.冠能狗粮小型犬美毛狗粮宠物狗比熊贵宾通用型小型犬狗粮小型成...10:1834评论 闭眼买、再降价、PLUS会员:尔蓝 压圈式垃圾桶 AL-GB109 6.92元包邮(需凑单0.9元) 12:2134评论 限用户:京东双11 话费充值补贴 实测中满10减5元话费券 赶紧去看看,先到先得 11月10日30评论 浏览记录 冠能狗粮 小型犬美毛狗粮 宠物狗比熊贵宾通用型小型犬狗粮 小型成犬粮7kg扫码...https://cu.manmanbuy.com/discuxiao_10349990.aspx
3.来了!纽顿T29狗粮测评!纽顿作为进口粮老品牌,其口碑和品质一直比较在线。今天我们要为大家测评一下纽顿T29狗粮,这款狗粮主打低脂低敏配方,比较适合小型犬,感兴趣的铲屎官可以一起来看看哦~ 生产工厂:Elmira Pet Products Ltd. 参考价格:32元/斤 一、购买 为了确保产品质量,我们此次购买的狗粮都是从纽顿线上旗舰店上购买的,纽顿品牌的知...https://www.isdpp.com/xq-17203.html
4.美味狗粮图片免费下载PNG素材编号z2rijnw2q编号:z2rijnw2q 尺寸:1024 x 669 像素 授权方式: 不可商用i 分享者:qwe 狗狗 卡通狗 手绘小狗 手绘狗 舌尖美味 狗粮猫粮 狗相框 猫粮狗粮 卡通狗狗 狗狗动 美味的狗粮PNGAI 卡通手绘狗粮猫粮素材PNGPSD 一堆零散狗粮PNG 猫粮狗粮PNG 猫粮狗粮PNG https://616pic.com/sucai/z2rijnw2q.html
5.QGDY0012017宠物喂食器企业标准(5页)GDY 001—2017 企业标准?可打印?可复制?无水印?高清原版?去除空白页 2017-02-23发布 2017-02-23实施 南京根达亚智能科技有限公司 发布 DDDDDDDDDDDD Q/GDY 001—2017 前 言 本标准按GB/T 1.1-2009 《标准化工作导则第1部分:标准的结构和编写》的规定编制,作为组织 生产和质量监督检验的依据。 https://max.book118.com/html/2020/0701/7045122153002144.shtm
6.狗粮啊?狗粮啊?开头的成语包含狗粮啊?的成语 狗咬狗 屯粮积草 兵精粮足 裹粮策马 寅吃卯粮 因敌取粮 狗心狗行 嫁狗逐狗 嫁狗随狗 飞刍挽粮 粮尽援绝 赍粮藉寇 馈贫之粮 寅支卯粮 吃粮不管事 飞粮挽秣 裹粮坐甲 积草屯粮 积草囤粮 粮多草广 弹尽粮绝 煮弩为粮 ...https://www.hao86.com/idiom_search/%E7%8B%97%E7%B2%AE%E5%95%8A%EF%BC%9F/
7.生产狗粮的利润有多大生产狗粮的利润有多大等待蓝色的枫叶落下 精选回答 1、以下是目前资本市场上从事宠物相关产业的某公司相关数据: 2、可以看到,宠物主粮的毛利大概是37%左右。当然,不同的公司、不同的宠物品牌,毛利都不尽相同,但是总体40%左右的利润还是有的。 3、而且,宠物的主要利润不仅是狗粮,还有后续消费品。比如宠物垫和玩具...https://edu.iask.sina.com.cn/jy/361QdoOYaND.html
1.宠物食品检测,狗粮检测机构狗粮检测标准(部分) 1、 t/zzb 0810-2018 宠物食品狗咬胶 2、 gb/t 31216-2014 全价宠物食品犬粮 3、 t/ciqa 15-2020冻干宠物食品规范 4、 t/sdpia 08-2022烘焙全价宠物食品 5、 t/sdpia 01-2023湿型全价宠物食品 6、 as 5812:2011宠物食品的生产和销售 7、 as 5812:2017宠物食品的制造和销售 8、...https://m.11467.com/product/d25185265.htm
2.问答:狗粮原味美版Orijen渴望进口狗粮原味通用11.4kg材质安全...[最佳答案]:Orijen渴望狗粮幼犬成犬全价犬粮 原味鸡肉11.4kg通用无谷进口是来自上海的【天猫超市】在售Orijen/原始猎食渴望品牌宠物/宠物食品及用品:狗全价膨化粮,可领30元优惠券后769元,【美版】Orijen渴望进口狗粮原味通用11.4kg,渴望进口狗粮原味,85%优质动物原料,鸡肉犬粮成犬幼犬通用看...https://www.dzlo.com/ask/1aacj9.html
3.酱香型白酒执行标准Q和GB有什么区别首先,Q标准是指《酱香型白酒技术规范(Q/JK 001-2015)》,是由中国酒类行业协会制定的标准。该标准...http://www.maixianwang.com/ask/172544.html
4.济宁狗粮山东狗粮济宁宠物食品山东省狗粮厂山东美可奇生物技术有限公司欢迎您!本公司是一家宠物食品研发、生产、销售于一体的现代化企业。所生产的爱犬人系列犬粮是由国内外著名宠物营养专家共同研发、采用顶级科研配方、国外先进加工工艺精制而成,涵盖各犬种所需营养成分,有利于爱犬成长发育,符合宠物营养需求,http://www.meikeqi.net/
5.GitHubProfond/FGO除战斗外,还提供包括但不限于以下功能:抽友情池,抽无限池,领邮箱狗粮,礼装强化 运行Run Windows 下载release - 运行游戏 - 运行FGO-py.bat- 连接设备 - 游戏中把你要刷的关卡放在第一个 - 点击「肝!」按钮 需要关闭「技能使用确认」 渠道服用户需要在初次运行后自行更改fgoConfig.json中package为自己的包名 ...https://github.com/Profond/FGO-py/tree/938e357467523c15f6f68cfaaabc035d5452e8c1
6.狗粮照片正版商用图片0mu41q摄图新视界提供狗粮图片下载,另有动物,背景,骨,骨头,棕色的,颜色,有色的,丰富多彩的,彩色的,五颜六色,饮食,多种多样的,狗,小狗,食物图片搜索供您浏览下载,每张图片均有版权可放心商用,您正在浏览的图片为0mu41qhttps://xsj.699pic.com/tupian/0mu41q.html
7.全价宠物食品狗粮一站式代加工oem工厂价格厂家¥5.50 狗粮代加工/狗粮OEM/猫粮代加工/猫粮OEM/山东宠物粮代加工贴牌 面议 狗粮代加工厂 猫粮代工厂排名 山东小顽童宠物食品代工厂 ¥5.50 山东宠物食品代加工 狗猫粮代工 狗粮批发 宠物零食贴牌代工 面议 山东狗粮猫粮代工厂瑞祥诺尔生产批发犬粮猫粮贴牌代加工1-20kg 青岛...https://www.china.cn/gougouganliang/4024328765.html
8.2020年11月营销日历知识库比如餐饮企业出荤劲牛堡,狗粮品牌出全肉粮,多肉植物卖家当天只售捕蝇草…… 感恩节 2020年11月26日 宜:玩跨界营销 2017的感恩节,杜蕾斯在感恩了 13 家品牌 杜蕾斯在各时间段的整点,于微博上感恩13个品牌:箭牌口香糖、德芙巧克力、士力架、Jeep、Levi's等。 https://www.shichangbu.com/know_info/55680.html
9.纯福狗粮来自是哪个厂家生产的–960化工网问答纯福狗粮是由广州市福康宠物食品有限公司生产场的,该公司成立于2008年,是一家专注于宠物食品研发、生产...https://m.chem960.com/ask/q-81aa7c81cd4f467798764545d55a606b
10.黄山有哪些茶叶普洱茶百科黄山作为中国著名的风景旅游区以其奇松、怪石、云海、泉四绝著称。黄山不仅风景秀丽更是茶叶的故乡其以黄山毛峰、太平猴魁等名茶闻名于世。这些茶叶不仅品质上乘外形也颇具特色有些甚至被形容为长得像狗粮。咱们解释落实... 黄山有哪些茶叶出名?黄山著名茶叶品种解析 黄山是...https://www.jiceng.org/post/puerchabk/1947244.html
11.python里面的进程和线程有什么区别python中的进程和线程p3.join()#生产者结束,——》q.join()——》消费者确实把所有数据都收到 #主进程结束之后,守护线程随之结束,这样消费者进程就不会存活 生产者消费者升级版 十、死锁现象与递归锁 进程也有死锁与递归锁,所谓死锁,是指两个或两个以上的进程或线程在执行过程中,因争夺资源而造成的一种互相等待的现象,若无外力...https://blog.csdn.net/weixin_39886238/article/details/110170166