所以我目前有以下方法,根据加权概率(based on this)随机返回一个字符串(一组已知的字符串):
def get_response(request)
responses = ['text1', 'text2', 'text3', 'text4', 'text5', 'text6']
weights = [5, 5, 10, 10, 20, 50]
ps = weights.map { |w| (Float w) / weights.reduce(:+) }
# => [0.05, 0.05, 0.1, 0.1, 0.2, 0.5]
weighted_response_hash = responses.zip(ps).to_h
# => {"text1"=>0.05, "text2"=>0.05, "text3"=>0.1, "text4"=>0.1, "text5"=>0.2, "text6"=>0.5}
response = weighted_response_hash.max_by { |_, weight| rand ** (1.0 / weight) }.first
response
end
现在不是随机加权输出,而是希望输出在输入字符串的基础上保持一致,同时保持响应的加权概率。例如,调用如:
get_response("This is my request")
应始终产生相同的输出,同时保持输出文本的加权概率。
我认为Modulo可以在某种程度上使用,哈希映射到相同的结果,但我有点丢失。
答案 0 :(得分:0)
@maxpleaner试图用this说的是
srand可用于确保程序的不同运行之间可重复的伪随机数序列。
因此,如果您为随机生成器播种,您将始终获得相同的结果。
例如,如果你这样做
func randomQuote(){
//Make an array from database keys
var authorArray = Array(database.keys)
//Pick a random author
let author = authorArray[Int(arc4random_uniform(UInt32(authorArray.count)))]
//Make an array from values based on the author we've picked
let quoteArray = database[author]!
//Pick a random quote from the choses author
let quote = quoteArray[Int(arc4random_uniform(UInt32(quoteArray.count)))]
print(author)
print(quote)
}
每当您传入相同的random = Random.new(request.hash)
response = weighted_response_hash.max_by { |_, weight| random.rand ** (1.0 / weight) }.first
时,您总会得到相同的response
。
旧代码
request
新代码,播种随机
3.times.collect { get_response('This is my Request') }
# => ["text6", "text1", "text6"]
3.times.collect { get_response('This is my Request 2') }
# => ["text6", "text4", "text5"]
输出仍然是加权的,刚才有一些可预测性:
3.times.collect { get_response('This is my Request') }
# => ["text4", "text4", "text4"]
3.times.collect { get_response('This is my Request 2') }
# => ["text1", "text1", "text1"]