用于最大化模数m的平方和的代码

时间:2017-04-05 14:18:31

标签: python algorithm python-3.x

输入:

k-> number of lists
m->modulo
Constraints
1<=k<=7
1<=M<=1000
1<=Magnitude of elements in list<=10*9
1<=Elements in each list<=7
` 

此代码段负责最大化(x1^2 + x2^2 + ...) % m,其中x1, x2, ...从列表X1, X2, ...中选择k,m=map(int,input().split()) Sum=0 s=[] for _ in range(k): s.append(max(map(int,input().split()))) Sum+=int(s[_])**2 print(Sum%m)

3 1000
2 5 4
3 7 8 9 
5 5 7 8 9 10 

例如,如果输入是:

m

输出将是206,因为在每个列表中选择最高元素,将该元素平方,取总和并使用(5^2+9^2+10^2)%1000=206执行模数运算

所以,它会是3 998 6 67828645 425092764 242723908 669696211 501122842 438815206 4 625649397 295060482 262686951 815352670 3 100876777 196900030 523615865

如果我提供像

这样的输入
974

预期输出为624,但我得到transform

我想知道您将如何处理此问题或如何更正现有代码。

4 个答案:

答案 0 :(得分:4)

你必须找到模数为m的最大值((平方和))。这与模数m的最大值(平方和)不同。

你可能会发现一个平方和不是绝对值,但是当你取模数时它是最大的。

例如:

m=100
[10, 9],
[10, 5]

这里,最大平方和是100 + 100 = 200,这是0模100。最大值(模数为100的平方和)是(81 + 100)= 182,即82模100。

鉴于m被迫小,有一个快速动态编程解决方案,在O(m * N)时间运行,其中N是所有列表中的项目总数。

def solve(m, xxs):
    r = [1] + [0] * (m - 1)
    for xs in xxs:
        s = [0] * m
        for i in xrange(m):
            for x in xs:
                xx = (x * x) % m
                s[i] += r[(i - xx) % m]
        r = s
    return max(i for i in xrange(m) if r[i])

m = 998
xxs = [
    [67828645, 425092764, 242723908, 669696211, 501122842, 438815206],
    [625649397, 295060482, 262686951, 815352670],
    [100876777, 196900030, 523615865]]

print solve(m, xxs)

根据需要输出974

答案 1 :(得分:1)

这里有一个重要的逻辑问题,你必须跳过每个列表中的项目数,同时在for循环中找到max元素。也就是说,而不是

实施例,

6 67828645 425092764 242723908 669696211 501122842 438815206

,您的数据是

67828645 425092764 242723908 669696211 501122842 438815206

即,

input().split()

你必须使用,

input().split()[1:]

正如Paul Hankin指出的那样,你基本上需要找到max(权力之和%m) 您必须从三个列表中找到组合,其总和%m是最大值

所以,基本上就是这样,

扫描输入,用空格分割,留下第一个元素,即每行中的值数,然后将它们映射到整数。然后,您找到方块并将它们附加到列表s。找到产品(itertools模块)示例 - 产品([1,2],[3,4,5])将给出,[(1,1),(1,2),(1,3), (2,1),(2,2),(2,3)]。现在,您可以找到每个这样的结果的总和%m并找到最大值!

即,

k,m=map(int,input().split())
from itertools import product
s=[]
for _ in range(k):
	s.append(map(lambda x:x**2,map(int,input().split()[1:])))
print(max([sum(i)%m for i in product(*s)]))

Try it online!

这将为您提供所需的输出!

希望它有所帮助!

答案 2 :(得分:0)

你的问题不是很清楚。但是,如果我理解正确,你有f(X1),...,f(Xn)的可能值列表(可能是通过对X1,...,Xn的所有可能值应用f得到的),然后你想要最大化f(X1)^2 + ... + f(Xn)^2

如果是这样,你的代码似乎很好,我得到了相同的结果:

lists = [[6, 67828645, 425092764, 242723908, 669696211, 501122842, 438815206],
[4, 625649397, 295060482, 262686951, 815352670],
[3, 100876777, 196900030, 523615865]]
sum = 0
for l in lists:
    sum += max(l)**2
print(sum%998)

此打印624,就像您的代码一样。你从哪里得到974?

答案 3 :(得分:0)

不会因此赢得任何代码高尔夫,但这是我的解决方案:

from functools import reduce


def get_input():
    """
    gets input from stdin.
    input format:
    3 1000
    2 5 4
    3 7 8 9
    5 5 7 8 9 10
    """
    k, m = [int(i) for i in input().split()]
    lists = []
    for _ in range(k):
        lists.append([int(i) for i in input().split()[1:]])
    return m, k, lists

def maximise(m, k, lists):
    """
    m is the number by which the sum of squares is modulo'd
    k is the number of lists in the list of lists
    lists is the list of lists containing vals to be sum of squared
    maximise aims to maximise S for:
    S = (f(x1) + f(x2)...+ f(xk)) % m
    where:
    f(x) = x**2
    """
    max_value = reduce(lambda x,y: x+y**2, [max(l) for l in lists], 0)
    # check whether the max sum of squares is greater than m
    # if it is the answer has to be the max
    if max_value < m:
        print(max_value)
        return
    results = []
    for product in cartesian_product(lists):
        S = reduce(lambda x, y: x + y**2, product, 0) % m
        if S == m-1:
            print(S)
            return
        results.append(S)

    print(max(results))

def cartesian_product(ll, accum=None):
    """
    all combinations of lists made by combining one element from 
    each list in a list of lists (cartesian product)
    """
    if not accum:
        accum = []
    for i in range(len(ll[0])):
        if len(ll) == 1:
            yield accum + [ll[0][i]]
        else:
            yield from cartesian_product(ll[1:], accum + [ll[0][i]])

if __name__ == "__main__":
    maximise(*get_input())