Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/apache-kafka/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
python配方:与值最接近的列表项_Python - Fatal编程技术网

python配方:与值最接近的列表项

python配方:与值最接近的列表项,python,Python,考虑到像[0,3,7,10,12,15,19,21]这样的列表,我想得到最接近任何值的最接近的最小数字,所以如果我通过4,我会得到3,如果我通过18,我会得到15,等等。a是列表,而b是值: max(a for a in a if a <= b) max(a表示a,如果a这里有几个选项 最简单的方法是迭代数组,并在a)到达数组末尾或b)当前位置的值大于您要查找的值时停止。然后简单地返回最后找到的值。(需要考虑的一种边缘情况:如果请求的数量小于数组的所有值,会发生什么情况?) 此解决方案假

考虑到像
[0,3,7,10,12,15,19,21]
这样的列表,我想得到最接近任何值的最接近的最小数字,所以如果我通过
4
,我会得到
3
,如果我通过
18
,我会得到
15
,等等。

a
是列表,而
b
是值:

max(a for a in a if a <= b)

max(a表示a,如果a这里有几个选项

最简单的方法是迭代数组,并在a)到达数组末尾或b)当前位置的值大于您要查找的值时停止。然后简单地返回最后找到的值。(需要考虑的一种边缘情况:如果请求的数量小于数组的所有值,会发生什么情况?)


此解决方案假定阵列是有序的。如果没有,它将不起作用。

如果您的列表很小,那么迭代它是最好的选择。您将避免一些开销,而且过度设计这项任务也没有意义。如果您希望您的代码更“正确”,或者希望它在更大的输入上更好地扩展,我建议使用二进制搜索方法。当然,这是假设您的输入保证被排序。如果未排序,则除了在跟踪增量的同时遍历值之外别无选择。下面是对二进制搜索策略的一个相对高级的解释:

  • 进行二进制搜索
  • 如果等于要搜索的值,则返回上一个索引处的值
  • 如果小于该值,则返回该索引
  • 如果大于该值,则返回上一个索引

  • 通过几个例子向自己证明这一点可能会有所帮助

    您可以使用
    yield
    next()
    来避免重复整个列表

    在线演示-


    这是一个非常混乱而且可能效率低下的解决方案,但它确实有效

    test=[0,3,7,10,12,15,19,21]
    value=25
    nearest=[]
    for i in test:
        if i == value:
            nearest.append(test[(test.index(i))])
            break
        if i>value:
            nearest.append(test[(test.index(i))-1])
            break
    if len(nearest) == 0:
        nearest.append(test[-1])
    
    print nearest[0]
    
    你可以用不太难的。它用于像这样的二进制搜索。这确实假设一个排序列表

    from bisect import bisect_right
    
    def find_le(a, x):
        'Find rightmost value less than or equal to x'
        i = bisect_right(a, x)
        if i:
            return a[i-1]
        raise ValueError
    
    mylist = [0,3,7,10,12,15,19,21]
    print find_le(mylist,4)
    print find_le(mylist,-1)
    print find_le(mylist,29)
    print find_le(mylist,12)
    
    运行交互式:

    >>> print find_le(mylist,4)
    3
    >>> print find_le(mylist,-1)
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "<stdin>", line 6, in find_le
    ValueError
    >>> print find_le(mylist,29)
    21
    >>> print find_le(mylist,12)
    12
    
    打印查找表(mylist,4) 3. >>>打印查找表(mylist,-1) 回溯(最近一次呼叫最后一次): 文件“”,第1行,在 文件“”,第6行,在查找表中 数值误差 >>>打印查找表(mylist,29) 21 >>>打印查找表(mylist,12) 12
    评论:

    (1.)我们不能假设原稿是预排序的,因为它没有被指定为预排序。因此,我做了一个就地排序。如果需要保留列表项的顺序,请复制列表,然后进行排序

    (2.)有一些使用对分模块和迭代器的优秀帖子。我想通过演示列表理解和一次性变量(下划线)的使用来展示另一种方法

    (3.)如果列表很长,则应使用对分。如果清单很短(规定不超过几百个),不要过度设计代码;线性搜索很好。请记住,在软件中,您总是在时间与空间、可读性、可维护性等之间进行折衷。

    使用对分
    一个问题是:一旦检查编号小于列表中的第一个元素,代码将给出最后一个元素

    import bisect
    lst = [0, 3, 7, 10, 12, 15, 19, 21]
    lst[bisect.bisect_left(lst,-1) - 1]
    

    它肯定不会给出正确的答案。@marcusshep这没什么区别Max而不是min当然,修复了它。你的意思是<代码>最大值(如果v中的v表示v,则列表是否总是排序?当您说“最接近的最小值”时你是指比输入值小的最大数字,还是delta真的很重要?如果值等于列表中的条目怎么办?我们应该转到下一个最大的数字还是返回相等的数字?根据他的例子,我想说我们不确定它是否被排序(可能不是因为他的答案没有排序)。我还想说,根据他的回答,他正在寻找相同的匹配项。虽然此代码可以回答这个问题,但提供了有关此代码为什么和/或如何回答该问题的附加上下文,以提高其长期价值。感谢您的反馈,Ajean!我将对我自己的代码进行评论,希望我能增加一些价值。
    x = [0,3,7,10,12,15,19,21]
    val = 18
    
    x.sort()
    close =  [abs(_ - val) for _ in x]
    ans = (x[close.index(min(close))])
    if ans > val:
        ans = (x[close.index(min(close)) -1])
    print (ans)
    
    import bisect
    lst = [0, 3, 7, 10, 12, 15, 19, 21]
    lst[bisect.bisect_left(lst,-1) - 1]