2012-07-30 44 views
26

Tôi cần kiểm tra xem Model.objects.filter(...) có bật lên bất kỳ thứ gì không, nhưng không cần phải chèn bất kỳ thứ gì. Mã của tôi cho đến nay là:Kiểm tra xem một đối tượng có tồn tại

user_pass = log_in(request.POST) # form class 
if user_pass.is_valid(): 
    cleaned_info = user_pass.cleaned_data 
    user_object = User.objects.filter(email = cleaned_info['username']) 
+0

tôi không hiểu những gì bạn đang cố gắng làm. Bạn đang cố gắng kiểm tra xem một người dùng đã tồn tại chưa? Tại sao bạn cần phải kiểm tra điều đó? Và tại sao bạn làm điều này trong một "dạng xem"? Hãy cố gắng trả lời câu hỏi này để xem chúng tôi có thể giúp bạn tốt hơn không ... Thêm ngữ cảnh cho vấn đề của bạn, không chỉ là câu hỏi mà bạn có trong đầu. Đôi khi vấn đề bạn nghĩ không phải là vấn đề thực sự, do đó câu hỏi bạn hỏi không đúng ... – marianobianchi

+0

Bản sao có thể có của [cách đúng để xác thực nếu một đối tượng tồn tại trong chế độ xem django mà không trả về 404 là gì?] (http://stackoverflow.com/questions/639836/what-is-the-right-way-to-validate-if-an-object-exists-in-a-django-view-without-r) – Wtower

Trả lời

33

Kể từ filter lợi nhuận một QuerySet, bạn có thể sử dụng count để kiểm tra có bao nhiêu kết quả trả về. Đây là giả định bạn không thực sự cần kết quả.

num_results = User.objects.filter(email = cleaned_info['username']).count() 

Sau khi xem xét các tài liệu, mặc dù nó tốt hơn để chỉ cần gọi len vào bộ lọc của bạn nếu bạn đang có kế hoạch về việc sử dụng các kết quả sau, khi bạn sẽ chỉ được đưa ra truy vấn một sql:

Một cuộc gọi count() thực hiện SELECT COUNT (*) đằng sau hậu trường, vì vậy bạn nên luôn sử dụng count() thay vì tải tất cả bản ghi vào các đối tượng Python và gọi len() trên kết quả (trừ khi bạn cần tải các đối tượng) vào bộ nhớ anyway, trong trường hợp len() sẽ nhanh hơn).

num_results = len(user_object) 
+50

Trong khi '. count() 'làm việc, bạn cũng có thể sử dụng' .exists() '. https://docs.djangoproject.com/en/dev/ref/models/querysets/#exists –

+3

Tôi muốn thêm vào nhận xét ở trên rằng trong khi .count() hoạt động, nó sẽ chậm hơn .exists() nếu số đếm> 1 và số đếm càng chậm thì nó sẽ trở thành – Bob

5

Bạn cũng có thể sử dụng get_object_or_404(), nó sẽ nâng cao một Http404 nếu đối tượng không được tìm thấy:

user_pass = log_in(request.POST) #form class 
if user_pass.is_valid(): 
    cleaned_info = user_pass.cleaned_data 
    user_object = get_object_or_404(User, email=cleaned_info['username']) 
    # User object found, you are good to go! 
    ... 
4

giá trị boolean của một QuerySet trống cũng là False, vì vậy bạn cũng có thể chỉ cần làm ...

... 
if not user_object: 
    do insert or whatever etc. 
+2

điều này không hiệu quả vì nó sẽ đánh giá truy vấn và khi đối tượng tồn tại, nó sẽ tải chúng vào bộ nhớ – mpaf

63

Tôi nghĩ dễ nhất từ ​​quan điểm logic và hiệu quả là sử dụng tập hợp truy vấn tồn tại() chức năng, tài liệu ở đây:

https://docs.djangoproject.com/en/dev/ref/models/querysets/#django.db.models.query.QuerySet.exists

Vì vậy, trong ví dụ của bạn ở trên tôi chỉ cần viết:

if User.objects.filter(email = cleaned_info['username']).exists(): 
    # at least one object satisfying query exists 
else: 
    # no object satisfying query exists 
2

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

try: 
    # get your models 
except ObjectDoesNotExist: 
    # do something 
Các vấn đề liên quan