欢迎光临
我们一直在努力

go语言学习例子No.1–打印网页源代码

参考 https://studygolang.com/pkgdoc

1.获取一个页面的html代码并打印输出

package main
import (
	"fmt"
	"io/ioutil"
	"log"
	"net/http"
)
func main() {
	//http.Get返回Response对象
	//追踪Get函数
	// func Get(url string) (resp *Response, err error) {
	// 	return DefaultClient.Get(url)
	// }
	//追踪DefaultClient
	// var DefaultClient = &Client{}
	//声明并赋值
	//Client实现了Get方法
	//我一直奇怪为什么我给了个地址,就能返回一个Response对象
	//然后Response对象里的Body就能存储信息,但是Body也是一个io.ReadCloser接口类型,他是怎么存储东西的
	res, err := http.Get("https://www.foxzc.com/archives/2020/08/13/359")
	if err != nil {
		log.Fatal(err)
	}
	result, err := ioutil.ReadAll(res.Body)
	//Body是io.ReadCloser
	//io.ReadCloser
	res.Body.Close()
	if err != nil {
		log.Fatal(err)
	}
	fmt.Printf("%s", result)//打印数据
}

2.获取一个页面的html代码并保存到文件

package main
import (
	"fmt"
	"io/ioutil"
	"log"
	"net/http"
)
func main() {
	//http.Get返回Response对象
	//追踪Get函数
	// func Get(url string) (resp *Response, err error) {
	// 	return DefaultClient.Get(url)
	// }
	//追踪DefaultClient
	// var DefaultClient = &Client{}
	//声明并赋值
	//Client实现了Get方法
	res, err := http.Get("https://www.foxzc.com/archives/2020/08/13/359")
	if err != nil {
		log.Fatal(err)
	}
	result, err := ioutil.ReadAll(res.Body)
	//Body是io.ReadCloser
	//io.ReadCloser
	res.Body.Close()
	if err != nil {
		log.Fatal(err)
	}
	//保存到文件
	err = ioutil.WriteFile("abc.html", result, 0777)
	if err != nil {
		log.Fatal(err)
	}
}

疑问点

对于我这样的新手来说,很难理解

//我一直奇怪为什么我给了个地址,就能返回一个Response对象
//然后Response对象里的Body就能存储信息,但是Body也是一个io.ReadCloser接口类型,他是怎么存储东西的

然后我写了个例子

package main
import "fmt"
type People struct { //定义一个People结构体类型
	Name string
}
type SetName interface { //People类型实现了SetName接口
	set()
}
//定义一个函数,接受People类型的参数,返回SetName类型
//这里要注意,因为People类型实现了SetName接口,所以可以把p当成SetName类型,但是反过来就不行,不能把SetName类型当成People类型
func (p People) set() {
	p.Name = "张三"
	fmt.Println("名字变成:", p.Name)
}
func do(p People) SetName {
	p.set()
	return p
}
func main() {
	var p = People{"李四"}
	fmt.Println("p原来是", p)
	do(p)
	fmt.Println("现在p是", p)
}
// p原来是 {李四}
// 名字变成: 张三
// 现在p是 {李四}

我们发现p没变,因为我们没传指针,他的作用域就只是在函数里,改写下

package main
import "fmt"
type People struct {
	Name string
}
type SetName interface {
	set()
}
func (p *People) set() {
	p.Name = "张三"
	fmt.Println("名字变成:", p.Name)
}
func do(p *People) SetName {
	p.set()
	return p
}
func main() {
	var p = &People{"李四"}
	fmt.Println("p原来是", p)
	do(p)
	fmt.Println("现在p是", p)
}
// p原来是 &{李四}
// 名字变成: 张三
// 现在p是 &{张三}

这个例子就是给了一个结构体对象,函数返回的是接口类型,也就是实现了这个接口的对象,这个对象里有数据,也可以再加个函数和People的全局变量,只传一个Name变量给结构体,这样就是上面我的疑问,为什么给个地址就能返回一个对象,再改写下

package main
import "fmt"
type People struct { //定义一个People结构体类型
	Name string
}
type SetName interface { //People类型实现了SetName接口
	set()
}
//定义一个函数,接受People类型的参数,返回SetName类型
//这里要注意,因为People类型实现了SetName接口,所以可以把p当成SetName类型,但是反过来就不行,不能把SetName类型当成People类型
func (p *People) set() {
	p.Name = "张三"
	fmt.Println("名字变成:", p.Name)
}
func do(p *People) SetName {
	p.set()
	return p
}
func setP(n string) *People { //因为是全局变量,DefaultPeople可以直接在函数里用
	DefaultPeople.Name = n
	return DefaultPeople
}
var DefaultPeople = &People{} //全局变量,就像上面的Client
func main() {
	p := setP("李四")
	fmt.Println("p原来是", p)
	do(p)
	fmt.Println("现在p是", p)
}
// p原来是 &{李四}
// 名字变成: 张三
// 现在p是 &{张三}

到这里应该可以理解我之前的疑惑了,再模仿上面的Get方法,传名字返回对象,改写下

package main
import "fmt"
type People struct { //定义一个People结构体类型
	Name string
}
type SetName interface { //People类型实现了SetName接口
	set()
}
//定义一个函数,接受People类型的参数,返回SetName类型
//这里要注意,因为People类型实现了SetName接口,所以可以把p当成SetName类型,但是反过来就不行,不能把SetName类型当成People类型
func (p *People) set() *People {
	p.Name = "张三"
	fmt.Println("名字变成:", p.Name)
	return p//返回对象
}
// func do(p *People) SetName {
// 	p.set()
// 	return p
// }
func setP(n string) *People { //因为是全局变量,DefaultPeople可以直接在函数里用
	DefaultPeople.Name = n
	return DefaultPeople.set()//结合上面的set方法,这样上面的do就省略了
}

var DefaultPeople = &People{} //全局变量,就像上面的Client

func main() {
	p := setP("李四")
	fmt.Println(p)
}
// 名字变成: 张三
// &{张三}

以上都是我个人编写的例子,仅供自己理解,也希望可以帮到你,大佬勿喷

 收藏 (0) 打赏

您可以选择一种方式赞助本站

支付宝扫一扫赞助

微信钱包扫描赞助

未经允许不得转载:家里蹲的狐狸 » go语言学习例子No.1–打印网页源代码

分享到: 生成海报
avatar

热门文章

  • 评论 抢沙发

    • QQ号
    • 昵称 (必填)
    • 邮箱 (必填)
    • 网址

    登录

    忘记密码 ?

    切换登录

    注册

    我们将发送一封验证邮件至你的邮箱, 请正确填写以完成账号注册和激活