Kiểm tra xem tất cả các giá trị trong danh sách có lớn hơn một số nhất định không


82
my_list1 = [30,34,56]
my_list2 = [29,500,43]

Làm cách nào để kiểm tra xem tất cả các giá trị trong danh sách có> = 30 hay không? my_list1nên làm việc và my_list2không nên.

Điều duy nhất tôi có thể nghĩ đến là:

boolean = 0
def func(ls):
    for k in ls:
        if k >= 30:
            boolean = boolean + 1
        else:
            boolean = 0
    if boolean > 0:
        print 'Continue'
    elif boolean = 0:
        pass

Cập nhật 2016:

Nhìn lại, sau khi xử lý các bộ dữ liệu lớn hơn, nơi tốc độ thực sự quan trọng và sử dụng numpy ... tôi sẽ làm điều này:

>>> my_list1 = [30,34,56]
>>> my_list2 = [29,500,43]

>>> import numpy as np
>>> A_1 = np.array(my_list1)
>>> A_2 = np.array(my_list2)

>>> A_1 >= 30
array([ True,  True,  True], dtype=bool)
>>> A_2 >= 30
array([False,  True,  True], dtype=bool)

>>> ((A_1 >= 30).sum() == A_1.size).astype(np.int)
1
>>> ((A_2 >= 30).sum() == A_2.size).astype(np.int)
0

Bạn cũng có thể làm điều gì đó như:

len([*filter(lambda x: x >= 30, my_list1)]) > 0

Một số vấn đề chung cần lưu ý: 1) booleanbiến được gán là cục bộ của hàm (vì không có globalchú thích thích hợp ) và 2) boolean = 0là một phép gán , không phải là một phép so sánh.
user2864740

Lưu ý rằng giá trị của bạn my_list1một giá trị không lớn hơn 30. Thay vào đó nó bằng 30. Thay vào đó, giá trị đó phải là 31, hay bạn đang kiểm tra giá trị lớn hơn hoặc bằng 30 ở đây?
Martijn Pieters

Câu trả lời:


141

Sử dụng all()hàm với biểu thức trình tạo:

>>> my_list1 = [30, 34, 56]
>>> my_list2 = [29, 500, 43]
>>> all(i >= 30 for i in my_list1)
True
>>> all(i >= 30 for i in my_list2)
False

Lưu ý rằng bài kiểm tra này lớn hơn hoặc bằng 30, nếu không my_list1sẽ không vượt qua bài kiểm tra.

Nếu bạn muốn thực hiện điều này trong một hàm, bạn sẽ sử dụng:

def all_30_or_up(ls):
    for i in ls:
        if i < 30:
            return False
    return True

Ví dụ: ngay sau khi bạn tìm thấy một giá trị chứng minh rằng có một giá trị dưới 30, bạn trả lại Falsevà trả lại Truenếu bạn không tìm thấy bằng chứng nào cho điều ngược lại.

Tương tự, bạn có thể sử dụng any()hàm để kiểm tra xem có ít nhất 1 giá trị phù hợp với điều kiện hay không.


Lợi thế của việc sử dụng all_30_or_uphơn là allgì? allCũng không nên ngừng sử dụng trình lặp ngay sau khi tìm thấy một tiêu cực? Nếu không sẽ khá ngớ ngẩn phải không?
Hyperboreus

1
@Hyperboreus: cả hai đều dừng ngay sau khi phát hiện ra âm tính. Tôi muốn cung cấp cho OP một cách nhìn khác về vấn đề, cung cấp cho họ một chức năng thay thế chức năng mà họ đang viết.
Martijn Pieters

@MartijnPieters, Mucho <3
zelusp

9

... bất kỳ lý do tại sao bạn không thể sử dụng min()?

def above(my_list, minimum):
    if min(my_list) >= minimum:
        print "All values are equal or above", minimum
    else:
        print "Not all values are equal or above", minimum

Tôi không biết liệu đây có phải chính xác những gì bạn muốn hay không, nhưng về mặt kỹ thuật, đây là những gì bạn yêu cầu ...


2
Nhược điểm của giải pháp này là, mỗi mục trong danh sách phải được chạm vào.
Hyperboreus

2
Tôi đã làm một hồ sơ nhỏ về điều này. allshortcircuits, vì vậy sẽ nhanh hơn nhiều nếu danh sách không đủ điều kiện. Nhưng nếu danh sách tất cả là 30+, mincó thể nhanh hơn. Tôi đã thử nghiệm với hai danh sách 1000 phần tử gồm các số nguyên ngẫu nhiên, một được điền random.randint(0, 100)(không đạt) và một được điền random.randint(30, 100). Sử dụng minmất ít hơn một nửa thời gian trong danh sách 30-100. Nhưng allchiếm khoảng 2% thời gian mincủa danh sách 0-100, vì vậy nó có thể thắng trừ khi danh sách thất bại là rất hiếm.
Peter DeGlopper

1
Hóa ra, phần tử đầu tiên trong danh sách 0-100 của tôi dưới 30, vì vậy bài kiểm tra của tôi thuộc loại suy biến. Buộc phần tử phụ 30 đầu tiên đi được nửa danh sách, sẽ minnhanh hơn một chút - 0,25 giây cho 10000 lần lặp lại thay vì 0,32 giây cho all. Vì vậy, cái nào nhanh hơn phụ thuộc vào bản chất của dữ liệu, như bạn mong đợi.
Peter DeGlopper

4

Có một chức năng nội trang all:

all (x > limit for x in my_list)

Giới hạn giá trị lớn hơn tất cả các số phải có.


Khi my_list1nên kiểm tra True, kiểm tra gần như chắc chắn nên có >= 30, không > 30.
Martijn Pieters

1
Chà, khi nội dung câu hỏi của OP mâu thuẫn với chính nó, tôi là ai để đánh giá đâu là giới hạn chính xác.
Hyperboreus

3

Bạn có thể sử dụng all():

my_list1 = [30,34,56]
my_list2 = [29,500,43]
if all(i >= 30 for i in my_list1):
    print 'yes'
if all(i >= 30 for i in my_list2):
    print 'no'

Lưu ý rằng điều này bao gồm tất cả các số bằng 30 trở lên, không hoàn toàn trên 30.


Khi my_list1nên kiểm tra True, kiểm tra gần như chắc chắn nên có >= 30, không > 30.
Martijn Pieters

@MartijnPieters cảm ơn, hiện đã được cập nhật. Câu hỏi đề cập trên 30 nhưng >= 30có vẻ như dự định.
Simeon Visser

Tôi biết, đó là lý do tại sao tôi nói rõ điều đó. :-)
Martijn Pieters

2

Người chiến thắng chung cuộc giữa việc sử dụng np.sum, np.min và tất cả dường như là np.min về tốc độ cho các mảng lớn:

N = 1000000
def func_sum(x):
    my_list = np.random.randn(N)
    return np.sum(my_list < x )==0

def func_min(x):
    my_list = np.random.randn(N)
    return np.min(my_list) >= x

def func_all(x):
    my_list = np.random.randn(N)
    return all(i >= x for i in my_list)

(tôi cần đặt định nghĩa np.array bên trong hàm, nếu không hàm np.min sẽ ghi nhớ giá trị và không thực hiện tính toán lại khi kiểm tra tốc độ với timeit)

Hiệu suất của "tất cả" phụ thuộc rất nhiều vào thời điểm phần tử đầu tiên không thỏa mãn tiêu chí được tìm thấy, np.sum cần thực hiện một chút phép toán, np.min là nhẹ nhất về tính toán trong trường hợp chung .

Khi các tiêu chí gần như được đáp ứng ngay lập tức và vòng lặp tất cả thoát ra nhanh chóng, hàm tất cả chỉ thắng hơn np.min một chút:

>>> %timeit func_sum(10)
10 loops, best of 3: 36.1 ms per loop

>>> %timeit func_min(10)
10 loops, best of 3: 35.1 ms per loop

>>> %timeit func_all(10)
10 loops, best of 3: 35 ms per loop

Nhưng khi "tất cả" cần phải đi qua tất cả các điểm, nó chắc chắn là tồi tệ hơn nhiều, và np.min chiến thắng:

>>> %timeit func_sum(-10)
10 loops, best of 3: 36.2 ms per loop

>>> %timeit func_min(-10)
10 loops, best of 3: 35.2 ms per loop

>>> %timeit func_all(-10)
10 loops, best of 3: 230 ms per loop

Nhưng sử dụng

np.sum(my_list<x)

có thể rất hữu ích là người ta muốn biết có bao nhiêu giá trị bên dưới x.


0

Bạn có thể làm như sau:

def Lists():

    my_list1 = [30,34,56]
    my_list2 = [29,500,43]

    for element in my_list1:
        print(element >= 30)

    for element in my_list2:
        print(element >= 30)

Lists()

Điều này sẽ trả về các giá trị lớn hơn 30 là True và các giá trị nhỏ hơn là false.


0

Tôi viết chức năng này

def larger(x, than=0):
    if not x or min(x) > than:
        return True
    return False

Sau đó

print larger([5, 6, 7], than=5)  # False
print larger([6, 7, 8], than=5)  # True
print larger([], than=5)  # True
print larger([6, 7, 8, None], than=5)  # False


Danh sách trống trên min () sẽ tăng ValueError. Vì vậy, tôi đã thêm if not xvào điều kiện.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.