跳过正文
爬虫遇到了点问题
  1. Posts/

爬虫遇到了点问题

·524 字·2 分钟· · ·
Golang 爬虫
小碗汤
作者
小碗汤
云原生搬砖师
Table of Contents

正文
#

golang爬珍爱网代码优化后,运行报了如下的错,找了半小时才找到原因,在此记录一下。

image

代码是这样的:

有一个interface类型的Parser:

type Parser interface {
	Parser(contents []byte, url string) ParserResult
	Serialize() (funcName string, args interface{})
}

有一个struct类型的FuncParser:

type FuncParser struct {
	parser ParserFunc
	funcName string
}

FuncParser 实现了Parser 接口:

func (f *FuncParser) Parser(contents []byte, url string) ParserResult {
	return f.Parser(contents, url)
}

func (f *FuncParser) Serialize() (funcName string, args interface{}) {
	return f.funcName, nil
}

抛开爬虫代码整体的复杂度,将代码简化到如下这样:

type ParserFunc func(url string) string

type FuncParser struct {
	parser ParserFunc
}

func (f *FuncParser) Parser(url string) string {
	return f.Parser(url)
}

func main() {

	funcParse := FuncParser{
		func(url string) string {
			return url
		},
	}

	funcParse.Parser("http://www.zhenai.com/zhenghun")
}

同样运行代码后同样会报错:

runtime: goroutine stack exceeds 1000000000-byte limit
fatal error: stack overflow

runtime stack:
runtime.throw(0x467297, 0xe)
	D:/Program Files/Go/go103/src/runtime/panic.go:616 +0x88
runtime.newstack()
	D:/Program Files/Go/go103/src/runtime/stack.go:1054 +0x72d
runtime.morestack()
	D:/Program Files/Go/go103/src/runtime/asm_amd64.s:480 +0x91

这个示例就很明显了,FuncParser的Parser里形成了递归调用(自己调自己),
递归调用自身导致栈溢出,导致报错。应该改成这样:(小写的parser)

image.png

实际上goland里已经提示了Recursive Call

image.png

一不小心就会写出这种代码,再看如下代码:

package main

import (
	"fmt"
)

type Str string

func (s Str) String() string {
	return fmt.Sprintf("Str: %s", s)
}

func main() {
	var s Str = "hi"
	fmt.Println(s)
}

同样报错:

image.png

You are implementing Str.String in terms of itself. return fmt.Sprintf(“Str: %s”, s) will call s.String(), resulting in infinite recursion. Convert s to string first.

This is working as intended, you are using the %s verb to call Str’s String method, which uses fmt.Sprint to call Str’s String method, and so on.

正常代码应该如下:

image.png

实际上,goland里也会警告该问题的:

image.png

看来平时编写代码,警告还是得注意的。

项目代码见: https://github.com/ll837448792/crawler

-------莫愁前路无知己 天下谁人不识君-------

相关文章

爬取珍爱网后用户信息展示
·3431 字·7 分钟·
Golang 爬虫
golang 设置 http response 响应头与坑
·1148 字·3 分钟·
Golang
java、golang日志文件转储压缩实现
·1473 字·3 分钟·
Golang Java 日志
beego与curl三件事
·1401 字·3 分钟·
Beego Golang Curl
go语言生成可执行文件
·629 字·2 分钟·
Golang
mysql支持原生json使用说明
·2478 字·5 分钟·
Mysql

公众号二维码