2012-03-16 28 views
5

Cố gắng viết một hàm cho hai chuỗi và trả về các ký tự giao nhau theo thứ tự chúng xuất hiện trong chuỗi đầu tiên.Python - Chuỗi giao giữa

Đây là những gì tôi đã cố gắng:

def strIntersection(str1, str2): 
    for i in str1: 
     str3 = '' 
     str3 = str3.join(i for i in str1 if i in str2 not in str3) 
    return str3 

str1 = 'asdfasdfasfd' 
str2 = 'qazwsxedc' 

strIntersection(str1,str2) 

=> 'asdasdasd' 

tuy nhiên tôi chỉ muốn các nhân vật ngã tư xuất hiện một lần và trong trật tự của chuỗi đầu tiên tức. 'asd'

Có ai giúp được không?

Tôi đã tìm thấy một số vấn đề tương tự như trên các diễn đàn khác, nhưng các giải pháp tất cả dường như liên quan đến danh sách trong khi tôi muốn đầu ra của tôi là một chuỗi

Trả lời

6

Kiểm tra cho lần xuất hiện cách khác xung quanh để có được thứ tự dưới sự kiểm soát và không phát ra các ký tự bạn đã phát ra:

def strIntersection(s1, s2): 
    out = "" 
    for c in s1: 
    if c in s2 and not c in out: 
     out += c 
    return out 

Chắc chắn bạn đồng uld viết lại nó là một danh sách hiểu, nhưng tôi thấy điều này dễ hiểu hơn.

Đối với dữ liệu thử nghiệm của bạn, chúng tôi nhận được:

>>> strIntersection('asdfasdfasfd' , 'qazwsxedc') 
'asd' 
+0

Cảm ơn! Nó chắc chắn là dễ hiểu hơn. Bây giờ tôi nhận ra rằng tôi đã làm phức tạp nó bằng cách cố gắng sử dụng '' join() – bang

+0

''' .join' là thành ngữ và không phức tạp chút nào. Tuy nhiên, sử dụng nó trong một vòng lặp, bỏ lỡ điểm. Trên thực tế, vòng lặp for trong mã OP hoàn toàn vô dụng; nó chỉ đơn giản là gây ra công việc thực tế - 'str3 = str3.join (i cho i trong str1 nếu i trong str2 không ở str3)' được thực hiện nhiều lần, với cùng một kết quả mỗi lần, và kết quả bị vứt bỏ mỗi lần nhưng cuối cùng. –

+0

Bạn không thể viết lại thuật toán cụ thể này để hiểu danh sách - ít nhất là không phải gọi một số công cụ không có giấy tờ đáng ngờ - vì bước lọc 'c trong s2 và c không ở ngoài' phụ thuộc vào kết quả từng phần cho đến thời điểm này , không thể truy cập được (ngoại trừ thông qua các nội dung không rõ ràng). –

7

Bạn muốn có một chuỗi gồm các nhân vật duy nhất là chung cho str1str2, theo thứ tự chúng xuất hiện trong str1.

Tính độc đáo và phổ biến ngụ ý thiết lập các hoạt động: nghĩa là, chúng tôi đang tìm tập hợp các ký tự xuất hiện trong cả str1 và str2. Một tập hợp về cơ bản là không có thứ tự, nhưng chúng tôi có thể sắp xếp lại dữ liệu bằng cách sắp xếp các ký tự theo "chỉ mục" của chúng trong lần xuất hiện đầu tiên trong str1. Sau đó, nó là một vấn đề đơn giản của việc tạo ra một chuỗi từ trình tự sắp xếp.

Đưa nó tất cả cùng nhau, chúng tôi nhận được:

''.join(sorted(set(str1) & set(str2), key = str1.index)) 
0

Dường như kịch bản hiện tại của bạn nên làm điều đó nếu bạn khắc phục lỗi đánh máy trên dòng thứ tư:

str3 = str3.join(i for i in str1 if i in str2 not in str3) 

nên

str3 = str3.join(i for i in str1 if i in str2 and i not in str3) 

Tôi sẽ không khuyên bạn nên sử dụng một bộ cho simpy này bởi vì họ không đảm bảo trật tự. Kịch bản của bạn cũng có khả năng nhanh hơn.

+0

Tôi khá chắc chắn những gì OP thực sự có nghĩa là '(i cho tôi trong str1 nếu tôi trong str2 và tôi không ở str3)'. Ngoại trừ việc này không có tác dụng vì 'str3' cần được so sánh so với vẫn chưa được xây dựng. Anh ta có logic của mình bối rối bằng cách cố gắng sử dụng cả vòng lặp for và comprehension. Đối với hiệu suất, tôi chắc chắn sẽ mong đợi phương pháp tiếp cận dựa trên 'set' nhanh hơn nhiều đối với các chuỗi dài. –

+0

@Karl: Có bạn nói đúng, tôi sẽ cập nhật câu trả lời của tôi. Nhưng so sánh với str3 không phải là một vấn đề vì nó chỉ cần kiểm tra phần đã được xây dựng. – aquavitae

+0

Vấn đề là 'str3' ** không **" phần đã được xây dựng ". Hoặc bạn thực thi mã này trong vòng lặp hoặc bạn không thực hiện. Nếu bạn không làm như vậy, thì 'str3' sẽ đưa ra một UnboundLocalError - bạn đang cố gắng ám chỉ đến thứ mà bạn đang gán cho nó. Nếu bạn làm thế, khi đó có 'tham gia' và hiểu không có ý nghĩa, vì bạn chỉ muốn xem xét ký tự hiện tại so với các ký tự giao nhau đã tìm thấy, không phải toàn bộ chuỗi. –

0
def str_intersection(str1, str2): 
    common_letters = set(str1) & set(str2) 
    str3 = '' 
    for c in str1: 
     if (c in common_letters) and (c not in str3): 
      str3 += c 
    return str3 
1

đơn giản nhất là sử dụng bộ trong python

>>> a='asdfasdfasfd' 
>>> b='qazwsxedc' 
>>> set(a).intersection(b) 
set(['a', 's', 'd']) 
+0

Việc này sẽ sao chép các câu trả lời hiện có và không cung cấp phân loại mà OP yêu cầu. –

Các vấn đề liên quan