简体   繁体   English

如何使用Python并遵循一组最小和最大要求在N个不均匀部分中划分数值?

[英]How to divide a number value in N unevenly parts using Python & following a set of min- & max requirement?

I have a fairly basic math problem in Python & I dont know where to look.我在 Python 中有一个相当基本的数学问题,我不知道去哪里找。

Explanation:解释:

  • I have 100 dollars.我有100美元。
  • I have 10 friends.我有10个朋友。
  • I want to unevenly distribute my money across my friends.我想在我的朋友之间不均匀地分配我的钱。
  • I want to this over & over again using a algorithm.我想一遍又一遍地使用算法。

My only requirements are the following:我唯一的要求如下:

  • The smallest amount any friend can receive should be > $5.任何朋友可以收到的最小金额应大于 5 美元。
  • The biggest amount any friend can receive should be < $40.任何朋友可以收到的最大金额应小于 40 美元。

from random import randint, shuffle

def divide_number(number, parts_number, allow_zero = False ):

    if (parts_number > number):
        raise ValueError("Number of parts can't be higher than the number");

    parts = {currency: []}
    number_rest = number

    for i in range(1, parts_number + 1):
        if (i == parts_number):
            parts[currency].append(number_rest)
            break
        else:
            new_number = randint(0, number_rest) if allow_zero else randint(1, (number_rest - 
(parts_number - i)) // 2)

        number_rest -= new_number
        parts[currency].append(new_number)

    return parts

Running the function:运行函数:

divide_number(100, 10)

Output输出

[2, 37, 8, 10, 2, 4, 4, 4, 26, 3]

This piece of code I've found online seems to work just great but it doesn't meet my requirements.我在网上找到的这段代码似乎很好用,但不符合我的要求。 How do I alter it so it does meet my requirements regarding min and max values?我如何改变它才能满足我对最小值最大值的要求?

So basicly, I want to go from unfair distribution to fair distribution .所以基本上,我想从不公平分配转向公平分配

在此处输入图片说明

Every next iteration you must ensure that you have enough money left to give at least minimum to all friends:每次下一次迭代时,您都必须确保有足够的钱留给所有朋友至少最低限度:

from random import randrange

def divide_number(number, divider, min_value, max_value):
    result = []
    for i in range(divider - 1, -1, -1):
        part = randrange(min_value, min(max_value, number - i * min_value + 1))
        result.append(part)
        number -= part
    return result

Usage:用法:

divide_number(100, 10, 5, 40)

Notice, that friends which took their part first will have much higher chance to get more.请注意,最先参与的朋友将有更高的机会获得更多。 You can make it a bit more "fair" by adding shuffle() right before function return:您可以通过在函数返回之前添加shuffle()使其更“公平”:

from random import shuffle

def divide_number(...):
    ...
    shuffle(result)
    return result

Is is not easy to make rather fair distribution with limits.在限制条件下进行相当公平的分配并不容易。 For reasonable sum and parts ( p ) values we can make p cells (friend pockets) and randomly put coin by coin into them (if possible)对于合理的总和和部分 ( p ) 值,我们可以制作 p 个单元格(朋友口袋)并随机将硬币一个硬币放入其中(如果可能)

import random

def randparts(summ, p, minn, maxx):
    maxx = maxx - minn
    summ -= p * minn
    if summ < 0:
        return None
    if p * maxx  >=  summ * 2:
        lst = [0] * p
        while summ > 0:
            r = random.randrange(p)
            if lst[r] < maxx:
                summ -= 1
                lst[r] += 1
    else:
        lst = [maxx] * p
        summ = maxx * p - summ
        while summ > 0:
            r = random.randrange(p)
            if lst[r] > 0:
                summ -= 1
                lst[r] -= 1
    for i in range(len(lst)):
        lst[i] += minn
    return lst

print(randparts(100, 10, 5, 40))

>>>[7, 17, 8, 10, 8, 8, 9, 12, 10, 11]

More concise and pythonic version from the comment of Olvin Roght (also removed the second branch for optimization for large summ values)更简洁,从Olvin Roght的注释Python的版本(也取消了优化第二支大型summ值)

def randparts(number, divider, min_value, max_value):
    sum_min = divider * min_value
    if sum_min > number:
        return

    number -= sum_min
    result = [min_value] * divider
    while number:
        pocket = randrange(divider)
        if result[pocket] <= max_value:
            result[pocket] += 1
            number -= 1

    return result

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 是否有任何 python 模块将数字 N 分成 3 个部分,使得这些部分的总和等于 N? 或者怎么做? - Is there any python module to divide a number N into 3 parts such that sum of that parts equal to N? or how to do that? 如何使用 Python 将未知整数分成给定数量的偶数部分 - How to divide an unknown integer into a given number of even parts using Python 如何将列表分成n个相等的部分,python - How to divide a list into n equal parts, python 如何在 Python 中将字符串分成“n”部分 - How to divide a string into 'n' parts in Python 如何在python中将数字分为多个不相等的部分? - How to divide a number into multiple unequal parts in python? 如何使用 python 重复部分剪辑 n 次 - How to repeat parts of clips n number of time using python 如何使用python查找文件中最小值和最大值的第一个实例? - How to find the first instance of a min and max value in a file using python? 如何在python中将多个循环'for'设置为函数的参数以找到将句号分成n部分的所有可能性? - How to set a number of loop 'for' as a parameter of a function in python to find all the possibility to cut a period in n parts? 如何使用python内置的最大值和最小值函数将给定列表的最大值和最小值转换为元组形式 - How to get max value and min value of a given list into tuple form with out using built in max and min function from python 如何计算将字符串分成任意大小的 N 个部分的方法数? - How can I count the number of ways to divide a string into N parts of any size?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM