From 7c36abc12f92b92f13c015529be8b9da84f4453c Mon Sep 17 00:00:00 2001 From: xiu2 <54703944+XIU2@users.noreply.github.com> Date: Wed, 31 May 2023 16:46:16 +0800 Subject: [PATCH] =?UTF-8?q?=E6=96=B0=E5=A2=9E=20[=E4=B8=A2=E5=8C=85?= =?UTF-8?q?=E5=87=A0=E7=8E=87=E4=B8=8A=E9=99=90]=20=E5=8F=82=E6=95=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- main.go | 13 ++++++++---- task/tcping.go | 4 ++-- utils/csv.go | 55 ++++++++++++++++++++++++++++++++------------------ 3 files changed, 46 insertions(+), 26 deletions(-) diff --git a/main.go b/main.go index 0c678fd..b9c1da6 100644 --- a/main.go +++ b/main.go @@ -46,9 +46,11 @@ https://github.com/XIU2/CloudflareSpeedTest 匹配指定地区;地区名为当地机场三字码,英文逗号分隔,仅 HTTPing 模式可用;(默认 所有地区) -tl 200 - 平均延迟上限;只输出低于指定平均延迟的 IP,可与其他上限/下限搭配;(默认 9999 ms) + 平均延迟上限;只输出低于指定平均延迟的 IP,各上下限条件可搭配使用;(默认 9999 ms) -tll 40 - 平均延迟下限;只输出高于指定平均延迟的 IP,可与其他上限/下限搭配;(默认 0 ms) + 平均延迟下限;只输出高于指定平均延迟的 IP;(默认 0 ms) + -tlr 0.2 + 丢包几率上限;只输出低于/等于指定丢包率的 IP,范围 0.00~1.00,0 过滤任何丢包的 IP;(默认 1.00) -sl 5 下载速度下限;只输出高于指定下载速度的 IP,凑够指定数量 [-dn] 才会停止测速;(默认 0.00 MB/s) @@ -72,6 +74,7 @@ https://github.com/XIU2/CloudflareSpeedTest 打印帮助说明 ` var minDelay, maxDelay, downloadTime int + var maxLossRate float64 flag.IntVar(&task.Routines, "n", 200, "延迟测速线程") flag.IntVar(&task.PingTimes, "t", 4, "延迟测速次数") flag.IntVar(&task.TestCount, "dn", 10, "下载测速数量") @@ -85,6 +88,7 @@ https://github.com/XIU2/CloudflareSpeedTest flag.IntVar(&maxDelay, "tl", 9999, "平均延迟上限") flag.IntVar(&minDelay, "tll", 0, "平均延迟下限") + flag.Float64Var(&maxLossRate, "tlr", 1, "丢包几率上限") flag.Float64Var(&task.MinSpeed, "sl", 0, "下载速度下限") flag.IntVar(&utils.PrintNum, "p", 10, "显示结果数量") @@ -104,6 +108,7 @@ https://github.com/XIU2/CloudflareSpeedTest } utils.InputMaxDelay = time.Duration(maxDelay) * time.Millisecond utils.InputMinDelay = time.Duration(minDelay) * time.Millisecond + utils.InputMaxLossRate = float32(maxLossRate) task.Timeout = time.Duration(downloadTime) * time.Second task.HttpingCFColomap = task.MapColoMap() @@ -125,8 +130,8 @@ func main() { fmt.Printf("# XIU2/CloudflareSpeedTest %s \n\n", version) - // 开始延迟测速 - pingData := task.NewPing().Run().FilterDelay() + // 开始延迟测速 + 过滤延迟/丢包 + pingData := task.NewPing().Run().FilterDelay().FilterLossRate() // 开始下载测速 speedData := task.TestDownloadSpeed(pingData) utils.ExportCsv(speedData) // 输出文件 diff --git a/task/tcping.go b/task/tcping.go index e868343..64779e8 100644 --- a/task/tcping.go +++ b/task/tcping.go @@ -64,9 +64,9 @@ func (p *Ping) Run() utils.PingDelaySet { return p.csv } if Httping { - fmt.Printf("开始延迟测速(模式:HTTP,端口:%d,平均延迟上限:%v ms,平均延迟下限:%v ms)\n", TCPPort, utils.InputMaxDelay.Milliseconds(), utils.InputMinDelay.Milliseconds()) + fmt.Printf("开始延迟测速(模式:HTTP,端口:%d,平均延迟上限:%v ms,平均延迟下限:%v ms,丢包几率上限:%.2f )\n", TCPPort, utils.InputMaxDelay.Milliseconds(), utils.InputMinDelay.Milliseconds(), utils.InputMaxLossRate) } else { - fmt.Printf("开始延迟测速(模式:TCP,端口:%d,平均延迟上限:%v ms,平均延迟下限:%v ms)\n", TCPPort, utils.InputMaxDelay.Milliseconds(), utils.InputMinDelay.Milliseconds()) + fmt.Printf("开始延迟测速(模式:TCP,端口:%d,平均延迟上限:%v ms,平均延迟下限:%v ms,丢包几率上限:%.2f )\n", TCPPort, utils.InputMaxDelay.Milliseconds(), utils.InputMinDelay.Milliseconds(), utils.InputMaxLossRate) } for _, ip := range p.ips { p.wg.Add(1) diff --git a/utils/csv.go b/utils/csv.go index e28ad36..ac48e27 100644 --- a/utils/csv.go +++ b/utils/csv.go @@ -11,16 +11,18 @@ import ( ) const ( - defaultOutput = "result.csv" - maxDelay = 9999 * time.Millisecond - minDelay = 0 * time.Millisecond + defaultOutput = "result.csv" + maxDelay = 9999 * time.Millisecond + minDelay = 0 * time.Millisecond + maxLossRate float32 = 1.0 ) var ( - InputMaxDelay = maxDelay - InputMinDelay = minDelay - Output = defaultOutput - PrintNum = 10 + InputMaxDelay = maxDelay + InputMinDelay = minDelay + InputMaxLossRate = maxLossRate + Output = defaultOutput + PrintNum = 10 ) // 是否打印测试结果 @@ -42,16 +44,17 @@ type PingData struct { type CloudflareIPData struct { *PingData - recvRate float32 + lossRate float32 DownloadSpeed float64 } -func (cf *CloudflareIPData) getRecvRate() float32 { - if cf.recvRate == 0 { +// 计算丢包率 +func (cf *CloudflareIPData) getLossRate() float32 { + if cf.lossRate == 0 { pingLost := cf.Sended - cf.Received - cf.recvRate = float32(pingLost) / float32(cf.Sended) + cf.lossRate = float32(pingLost) / float32(cf.Sended) } - return cf.recvRate + return cf.lossRate } func (cf *CloudflareIPData) toString() []string { @@ -59,7 +62,7 @@ func (cf *CloudflareIPData) toString() []string { result[0] = cf.IP.String() result[1] = strconv.Itoa(cf.Sended) result[2] = strconv.Itoa(cf.Received) - result[3] = strconv.FormatFloat(float64(cf.getRecvRate()), 'f', 2, 32) + result[3] = strconv.FormatFloat(float64(cf.getLossRate()), 'f', 2, 32) result[4] = strconv.FormatFloat(cf.Delay.Seconds()*1000, 'f', 2, 32) result[5] = strconv.FormatFloat(cf.DownloadSpeed/1024/1024, 'f', 2, 32) return result @@ -89,8 +92,10 @@ func convertToString(data []CloudflareIPData) [][]string { return result } +// 延迟丢包排序 type PingDelaySet []CloudflareIPData +// 延迟条件过滤 func (s PingDelaySet) FilterDelay() (data PingDelaySet) { if InputMaxDelay > maxDelay || InputMinDelay < minDelay { // 当输入的延迟条件不在默认范围内时,不进行过滤 return s @@ -99,10 +104,10 @@ func (s PingDelaySet) FilterDelay() (data PingDelaySet) { return s } for _, v := range s { - if v.Delay > InputMaxDelay { // 平均延迟上限 + if v.Delay > InputMaxDelay { // 平均延迟上限,延迟大于条件最大值时,后面的数据都不满足条件,直接跳出循环 break } - if v.Delay < InputMinDelay { // 平均延迟下限 + if v.Delay < InputMinDelay { // 平均延迟下限,延迟小于条件最小值时,不满足条件,跳过 continue } data = append(data, v) // 延迟满足条件时,添加到新数组中 @@ -110,18 +115,30 @@ func (s PingDelaySet) FilterDelay() (data PingDelaySet) { return } +// 丢包条件过滤 +func (s PingDelaySet) FilterLossRate() (data PingDelaySet) { + if InputMaxLossRate >= maxLossRate { // 当输入的丢包条件为默认值时,不进行过滤 + return s + } + for _, v := range s { + if v.getLossRate() > InputMaxLossRate { // 丢包几率上限 + break + } + data = append(data, v) // 丢包率满足条件时,添加到新数组中 + } + return +} + func (s PingDelaySet) Len() int { return len(s) } - func (s PingDelaySet) Less(i, j int) bool { - iRate, jRate := s[i].getRecvRate(), s[j].getRecvRate() + iRate, jRate := s[i].getLossRate(), s[j].getLossRate() if iRate != jRate { return iRate < jRate } return s[i].Delay < s[j].Delay } - func (s PingDelaySet) Swap(i, j int) { s[i], s[j] = s[j], s[i] } @@ -132,11 +149,9 @@ type DownloadSpeedSet []CloudflareIPData func (s DownloadSpeedSet) Len() int { return len(s) } - func (s DownloadSpeedSet) Less(i, j int) bool { return s[i].DownloadSpeed > s[j].DownloadSpeed } - func (s DownloadSpeedSet) Swap(i, j int) { s[i], s[j] = s[j], s[i] }