我們之前說(shuō)過(guò)了,我們先從單任務(wù)版開始進(jìn)行。蕾管。。。。
這里我們先給單任務(wù)版爬蟲定一個(gè)小目標(biāo)
- 獲取并打印所在城市第一頁(yè)用戶的詳細(xì)信息
stevendeAir:js_crawler steven$ pwd
/Users/steven/learngo/src/learn/js_crawler
stevendeAir:js_crawler steven$ ls
main.go
我們首先給這個(gè)項(xiàng)目建一個(gè)文件夾,名字為js_crawler,之后建了一個(gè)main.go文件
// main.go
package main
import (
"net/http"
"io/ioutil"
"fmt"
)
func main() {
// 首先我們使用get請(qǐng)求这刷,拿到響應(yīng)的結(jié)果resp
resp, err := http.Get(
"http://www.zhenai.com/zhenghun")
// 對(duì)錯(cuò)誤的處理,go就是這么處理的不像其他的語(yǔ)言應(yīng)try
if err != nil{
panic(err)
}
// 請(qǐng)求完成以后我們需要把這個(gè)流關(guān)上
defer resp.Body.Close()
// 如果請(qǐng)求不是200我們把狀態(tài)碼打出來(lái)
if resp.StatusCode != http.StatusOK{
fmt.Println("Error: Status code",
resp.StatusCode)
return
}
// 讀取Body里面的內(nèi)容
all, err := ioutil.ReadAll(resp.Body)
if err != nil{
panic(err)
}
fmt.Printf("%s\n", all)
}
很好,我們的頁(yè)面打印出來(lái)了但是我們發(fā)現(xiàn)它是亂碼啼县,這個(gè)是為什么呢?應(yīng)該怎么辦呢窑睁?
這是因?yàn)镚o語(yǔ)言都是utf8編碼吓著,但是我們這個(gè)網(wǎng)頁(yè)的是gbk編碼所以就出現(xiàn)了亂碼惕耕,沒(méi)關(guān)系我們解決它挤安。剿干。撰洗。。
我們只需要把gbk轉(zhuǎn)成utf8就可以了,這里我們需要下載兩個(gè)包看下面
stevendeAir:js_crawler steven$ gopm get -g -v golang.org/x/text
[GOPM] 05-27 12:14:41 [ INFO] App Version: 0.8.8.0307 Beta
[GOPM] 05-27 12:14:41 [ INFO] Local repository path: /Users/steven/.gopm/repos
[GOPM] 05-27 12:14:41 [ INFO] Indicated GOPATH: /Users/steven/learngo
[GOPM] 05-27 12:14:41 [ INFO] /Users/steven/.gopm/repos/golang.org/x/text
[GOPM] 05-27 12:14:41 [DEBUG] Skipped installed package: golang.org/x/text@branch:<UTD>
[GOPM] 05-27 12:14:41 [ WARN] Package in GOPATH has version control: golang.org/x/text
[GOPM] 05-27 12:14:41 [ INFO] 0 package(s) downloaded, 0 failed
它說(shuō)Skipped installed package西轩,這說(shuō)明我已經(jīng)安裝過(guò)了注服,現(xiàn)在可以直接使用了
我們把之前的resp.Body改成轉(zhuǎn)碼以后的就可以了
utf8Reader := transform.NewReader(
resp.Body, simplifiedchinese.GBK.NewDecoder())
// 讀取Body里面的內(nèi)容
all, err := ioutil.ReadAll(utf8Reader)
ok,到此呢我們的問(wèn)題解決了苇本,但是呢這么做并不通用裳凸,因?yàn)橐院笪覀兛赡軙?huì)有其它的編碼也會(huì)出現(xiàn)亂碼梦湘,那么怎么才能通用呢倦逐,我們可以去獲取網(wǎng)頁(yè)上面的charset然后轉(zhuǎn)成utf8是不是就可以了呢?其實(shí)有時(shí)候會(huì)有變態(tài)的網(wǎng)頁(yè)連meta也沒(méi)有我們?cè)趺醋瞿兀科鋵?shí)這里我們用到了Go語(yǔ)言的一個(gè)包可以直接獲取網(wǎng)頁(yè)的編碼看下面筑辨。楚昭。。。
stevendeAir:js_crawler steven$ gopm get -g -v golang.org/x/net/html
[GOPM] 05-27 12:23:05 [ INFO] App Version: 0.8.8.0307 Beta
[GOPM] 05-27 12:23:05 [ INFO] Local repository path: /Users/steven/.gopm/repos
[GOPM] 05-27 12:23:05 [ INFO] Indicated GOPATH: /Users/steven/learngo
[GOPM] 05-27 12:23:05 [ INFO] /Users/steven/.gopm/repos/golang.org/x/net
[GOPM] 05-27 12:23:05 [DEBUG] Skipped installed package: golang.org/x/net/html@branch:<UTD>
同樣的我也安裝好了珍促,直接用一把。。
// 定義一個(gè)解析的函數(shù)
func determineEncoding(r io.Reader) encoding.Encoding{
// 我們可以把它放到Peek里面下回繼續(xù)讀
// 如果我們不用Peek,它讀完1024以后就不會(huì)在讀這1024個(gè)字節(jié)了
// Peek 返回緩存的一個(gè)切片带膀,該切片引用緩存中前 n 字節(jié)數(shù)據(jù)
bytes, err := bufio.NewReader(r).Peek(1024)
if err != nil{
panic(err)
}
e, _, _ := charset.DetermineEncoding(bytes, "")
return e
}
然后把上面的resp.Body處理一下喂击。。。。
e := determineEncoding(resp.Body)
utf8Reader := transform.NewReader(
resp.Body, e.NewDecoder())
為了讓大家可以清楚的看到我的目錄結(jié)構(gòu)润绎,我會(huì)在代碼的上面放上這段代碼所在的文件位置,方便你的查看巡李。比如說(shuō)上面這段代碼在main.go文件里面,在開發(fā)的過(guò)程中我也會(huì)把代碼層次結(jié)構(gòu)發(fā)給大家与涡,不用擔(dān)心跟不上。恳守。。蛮寂。骄恶。你真實(shí)寫代碼的時(shí)候,上面的main.go就不需要加了:瞿酢8猜摹!竞慢!
怎么樣這一節(jié)看完了,你跟著操作了嘛沟饥,成功了嘛!P谧濉J匚省K砸恰!相种!