You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Go语言基于Channel实现计数器出现跳值问题求助

问题分析与解决

问题概述

编写的Go HTTP服务器程序,预期在页面上依次显示0、1、2……递增的计数器值,但实际输出为0、2、4、6……的跳值情况。

源代码

package main

import (
    "fmt"
    "log"
    "net/http"
)

type nextChan chan int 

func(ch nextChan) handle(writer http.ResponseWriter, req *http.Request){
    fmt.Fprintf(writer,"<h1> Counter value is %d </h1>",<-ch)
}

func counter(ch chan <-int){
    for i:=0; ;i++{
        ch <- i
    }
}

func main(){
    var nextId nextChan = make(chan int)
    go counter(nextId)
    http.HandleFunc("/",nextId.handle)
    log.Fatal(http.ListenAndServe(":8080",nil))
}

原因解析

跳值的核心原因是浏览器会自动发送额外请求:当你访问页面时,浏览器除了请求根路径/,还会自动请求/favicon.ico(用于显示页面标签栏图标)。每次请求都会触发handle函数,从Channel中读取一个计数器值。

比如:

  • 首次访问:/请求读取0(页面显示0),/favicon.ico请求读取1(该值被消耗但无可见输出)
  • 刷新页面:/请求读取2(页面显示2),/favicon.ico请求读取3(同样被隐藏消耗)
    循环往复,就出现了页面显示值跳增的情况。

解决方案

只需过滤非根路径的请求,避免额外请求消耗Channel值,有两种常见实现方式:

方式1:在handle函数中判断请求路径

func(ch nextChan) handle(writer http.ResponseWriter, req *http.Request){
    // 仅处理根路径请求,其他路径返回404
    if req.URL.Path != "/" {
        http.NotFound(writer, req)
        return
    }
    fmt.Fprintf(writer,"<h1> Counter value is %d </h1>",<-ch)
}

方式2:单独注册favicon的空处理函数

func main(){
    var nextId nextChan = make(chan int)
    go counter(nextId)
    http.HandleFunc("/",nextId.handle)
    // 给favicon注册空处理函数,不消耗计数器值
    http.HandleFunc("/favicon.ico", func(w http.ResponseWriter, r *http.Request) {})
    log.Fatal(http.ListenAndServe(":8080",nil))
}

内容的提问来源于stack exchange,提问作者Shivam...

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.30 03:42:42