one-api 渠道权重

ej83mcc0  于 2个月前  发布在  其他
关注(0)|答案(3)|浏览(40)

例行检查

  • 我已确认目前没有类似问题
  • 我已确认我已升级到最新版本
  • 我理解并愿意跟进此问题,协助测试和提供反馈
  • 我理解并认可上述内容,并理解项目维护者精力有限,不遵循规则的问题可能会被无视或直接关闭

功能描述

注意到 channel 表有 weight 字段,代码层面没有利用,只是随机选了可用渠道,希望能开放这个设置渠道权重的特性

应用场景

bqjvbblv

bqjvbblv1#

目前,随机选择配合分组已经能应付大部分场景了。

ix0qys7i

ix0qys7i2#

考虑两种实现方式:

  1. 加权随机,时间复杂度 O(n)
  2. 分组随机,分组可以设置权重,时间复杂度 O(1)
7jmck4yq

7jmck4yq3#

加权随机的一种实现方式:

package main

import (
	"fmt"
	"math/rand"
	"sort"
)

type Item struct {
	Name   string
	Weight int
}

type WeightedRandom struct {
	Items       []Item
	TotalWeight int
}

func NewWeightedRandom(items []Item) *WeightedRandom {
	totalWeight := 0
	for _, item := range items {
		totalWeight += item.Weight
	}

	return &WeightedRandom{
		Items:       items,
		TotalWeight: totalWeight,
	}
}

func (wr *WeightedRandom) GetRandomItem() Item {
	randWeight := rand.Intn(wr.TotalWeight)

	sort.SliceStable(wr.Items, func(i, j int) bool {
		return wr.Items[i].Weight < wr.Items[j].Weight
	})

	for _, item := range wr.Items {
		if randWeight < item.Weight {
			return item
		}
		randWeight -= item.Weight
	}

	return Item{}
}

func main() {
	items := []Item{
		{Name: "A", Weight: 4},
		{Name: "B", Weight: 3},
		{Name: "C", Weight: 2},
		{Name: "D", Weight: 1},
	}

	weightedRandom := NewWeightedRandom(items)
	var count = make(map[string]int)
	times := 100000
	for i := 0; i < times; i++ {
		item := weightedRandom.GetRandomItem()
		count[item.Name]++
	}
	for k, v := range count {
		fmt.Printf("%s: %.2f\n", k, float64(v)/float64(times))
	}
}

相关问题