用Go写的爬取网站上的图片

Go语言实现网页图片爬取
本文介绍如何使用Go(Golang)语言编写一个爬虫程序,从指定网站上抓取并下载图片。通过示例代码展示Go在爬虫领域的应用。

用Go写的爬取网站上的图片

package main

import (
	"fmt"
	"io"
	"log"
	"net/http"
	"os"
	"strings"
	"sync"

	"golang.org/x/net/html"
)

//打开互斥锁
var wg sync.WaitGroup

//获取网页里面包含jpg和htm的url并保存成切片
func getHtml(url string) ([]string, error) {
	res, err := http.Get(url)
	if err != nil {
		log.Fatal(err)
		return nil, err
	}
	defer res.Body.Close()
	htmlNode, err := html.Parse(res.Body)
	if err != nil {
		log.Fatal(err)
		return nil, err
	}
	imgUrlSlice := getImage(htmlNode, nil)
	return imgUrlSlice, nil
}

//递归调用DOM节点
func getImage(n *html.Node, imgSlice []string) []string {
	if n.Type == html.ElementNode || n.Data == "IMG" {
		for _, v := range n.Attr {
			imgSlice = append(imgSlice, v.Val)
		}
	}
	for c := n.FirstChild; c != nil; c = c.NextSibling {
		imgSlice = getImage(c, imgSlice)
	}
	return imgSlice
}

//下载并保存图片
func downPic(path, url string) {
	idx := strings.LastIndex(url, "/") + 1
	if idx < 0 {
		fmt.Println("获取文件url错误")
		return
	}
	filename := url[idx:]
	fp, err := os.Create(path + filename)
	if err != nil {
		log.Fatal(err)
	}
	defer fp.Close()
	res, err := http.Get(url)
	if err != nil {
		log.Fatal(err)
		return
	}
	defer res.Body.Close()
	io.Copy(fp, res.Body)
	wg.Done()
}
func main() {
	var picSlice = make([]string, 0)
	var htmSlice = make([]string, 0)
	var domain = "http://big5.cri.cn"
	url := domain + "/gate/big5/news.cri.cn/gb/9964/2007/08/27/1326@1734234.htm"
	/*
		1、首先lice获取到的是一个杂乱无章的jpg和htm组和的切片,而且有些图片也不是我想要的图片,可以过滤来实现
		2、循环切片如果是jpg的图片就存到picSlice切片中,如果是htm的网页就存到htmSlice切片中
		3、循环htmlSlice保存的页面,并继续过滤网页里面的jpg图片并追加保存到picSlice切片中
		4、利用多个协程把图片下载到文件夹下面
	*/
	slice, _ := getHtml(url)
	for _, v := range slice {
		if strings.Contains(v, "mmsource") {
			picSlice = append(picSlice, v)
		} else if strings.Contains(v, "9964") {
			htmSlice = append(htmSlice, v)
		}
	}
	for i := 0; i < len(htmSlice); i++ {
		slice2, _ := getHtml(domain + htmSlice[i])
		for _, v := range slice2 {
			if strings.Contains(v, "mmsource") {
				picSlice = append(picSlice, v)
			}
		}
	}
	wg.Add(len(picSlice))
	for _, v := range picSlice {
		go downPic("pic/", domain+v)
	}
	wg.Wait()
	fmt.Println("已经完成")
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值