El fin de la contabilidad son las matemáticas.

De todas formas el título del artículo siempre debería ser un poquito más interesante. El siguiente es un programa adecuado para encontrar soluciones enteras positivas a ecuaciones lineales de múltiples variables. Los números requeridos son todos números enteros positivos. La mejor situación es cuando el valor del elemento está lejos de la suma y no tiene sentido si está demasiado cerca. Dado que se acerca a una enumeración de fuerza bruta, es mejor no tener demasiadas variables. Personalmente lo probé por 5 yuanes y estuvo bien, pero sentí ganas de llorar cuando subí.

Hablando por experiencia, los números aleatorios se calculan más rápido que el recorrido. Si una ejecución lleva demasiado tiempo, puede detenerse y ejecutar nuevamente, y es posible que salga en un tiempo. Para decirlo sin rodeos, es una cuestión de ingeniería y se trata de usabilidad, pero la lógica no es lo suficientemente rigurosa.

Bienvenido a usarlo, ¡es una buena idea!

Si hay una lógica mejor, comente para dar su opinión. Después de la práctica, si usa aleatorio por 3 yuanes o más, la experiencia de velocidad será mejor y el cálculo será más rápido. Cada vez que lo paso, tengo que empezar de nuevo, esperando sin cesar.

import numpy as np
import random

def has_result(list_of_cost,total_amount):
    arr = np.array(list_of_cost)
    int_gcd = np.gcd.reduce(arr)
    return (total_amount % int_gcd == 0)

def volume_calc(list_of_cost,total_amount): 
    number_of_parts = len(list_of_cost)
    list_of_cost.sort(reverse=True)  #升序排序,大的成本在前。
    item_max_range = []
    item_parity_range = []
    for i in list_of_cost:
        item_max_range.append(total_amount // i + 1)    #每个成分货品的顶格数量。
    for i in list_of_cost:
        item_parity_range.append(total_amount // i // number_of_parts + 1)    #差不多1/n的金额数量的位置。 
    flag = 0
    item_volume_max = 0
    item_volume_min = item_parity_range[0]
    item_middle_range = item_parity_range.copy() 可一定得用copy,不然是传递性的。
    while flag == 0: 
        print("stupid loop!")
        krr = []
        for item in list_of_cost:
            item_number = list_of_cost.index(item)
            if item == max(list_of_cost):
                krr.append(item * item_volume_min)
            elif item != min(list_of_cost):
                    krr.append(item * item_middle_range[item_number])
                    continue
            else:
                while total_amount > (sum(krr) + item * item_volume_max):
                    item_volume_max = item_volume_max + 1
                if sum(krr) + item * item_volume_max == total_amount:
                    flag = 1
                    if number_of_parts == 3:
                        print(item_volume_min, item_middle_range[1],item_volume_max)
                    else:
                        print(item_volume_min, item_middle_range[1:-1],item_volume_max) 
                    break
                else:
                    if item_volume_min -1 > 0:
                        item_volume_min = item_volume_min - 1
                    else:
                        item_volume_min = item_max_range[0] 
                    if number_of_parts == 3:                       
                        item_middle_range[1] =  item_middle_range[1] - random.randrange(9) #这边会给盯着死减
                        if  item_middle_range[1] < 0:
                            item_middle_range[1] = item_parity_range[1]
                        break
                    elif number_of_parts > 3:
                        list_items = range(number_of_parts) 
                        random_item = random.choice(list_items[1:-1]) # max与min不会被选到调整最大值
                        item_middle_range[random_item] =  item_middle_range[random_item] - random.randrange(9)
                        if item_middle_range[random_item] < 0:
                            item_middle_range[random_item] = item_parity_range[random_item]
                        break
                    else:
                        print("new round...", item_volume_min,item_volume_max)
                        item_volume_max = 0 
                        break 
    return 0


def minor_mod_price(list_of_cost):  #minor mod cost
    list_of_random = [1,2,3,5,7]  # all prime numbers
    arr = np.array(list_of_cost)
    n_arr = len(arr)
    while np.gcd.reduce(arr) !=1: 
        item_num = random.randrange(n_arr)
        arr[item_num] = arr[item_num] + random.choice(list_of_random)
        print("calculating with changed No.%d, and changing to %f ",item_num,arr[item_num])
    return arr
   

if __name__ == "__main__":
    #此处有个中心思想,成本的数字远小于总的金额数,才导致了需要程序凑,不然的话,人脑就可以凑出来。
    list_costs = [311,153,146,56] #最好按从大到小给,因为后续也会这么sort。
    total_amt = 28000
    if has_result(list_costs,total_amt):
        volume_calc(list_costs,total_amt)
    else:
        print("the combination cannot get proper integer volume for use!")
        #print(minor_mod_price(list_costs))   # 如果成本金额的数字允许微调,可以考虑用这个函数馊主意。

Pensé en usar Sympy, y el Diophantine que contenía era algo bueno, pero el problema es que para usar esto, supongo que mi nivel de matemáticas debe ser más alto. Mi comprensión abstracta no es buena y mi base no es buena, por lo que solo puedo usar el pensamiento lineal para resolverlo.

2023-05-01: De hecho, puede mantener el resto sin cambios, pero agregue una capa de subprocesos múltiples para que el cálculo sea más rápido.

Supongo que te gusta

Origin blog.csdn.net/u011410413/article/details/130212614
Recomendado
Clasificación