2012-03-30 16 views
8

Tôi cần phải kết hợp các dòng trong hai tệp, căn cứ vào điều kiện, trong dòng của một trong các tệp là một phần của dòng của tệp thứ hai.Làm thế nào để kết hợp các dòng trong hai tập tin với điều kiện trong python?

Một phần của tập tin đầu tiên:

 
12319000 -64,7357668067227 -0,1111052148685535 
12319000 -79,68527661064425 -0,13231739777754026 
12319000 -94,69642857142858 -0,15117839559513543  
12319000 -109,59301470588237 -0,18277783185642743 
12319001 99,70264355742297 0,48329515727315125 
12319001 84,61113445378152 0,4060446341409862 
12319001 69,7032037815126 0,29803063228455073 
12319001 54,93886554621849 0,20958105041136763 
12319001 39,937394957983194 0,13623056582981297 
12319001 25,05574229691877 0,07748669438398018 
12319001 9,99716386554622 0,028110643107892755 

Một phần của tập tin thứ hai:

 
12319000.abf mutant 1 
12319001.abf mutant 2 
12319002.abf mutant 3 

tôi cần phải tạo một tập tin, nơi dòng bao gồm này: tất cả các dòng từ tệp đầu tiên và mọi thứ từ dòng thứ hai. ngoại trừ tên tệp trong cột đầu tiên.

Như bạn có thể thấy, có nhiều hơn một dòng trong tệp đầu tiên, cooresponding vào một dòng trong tệp thứ hai. Tôi cần hoạt động đó được thực hiện với mỗi dòng, vì vậy sản lượng nên được như thế này:

 
12319000 -94,69642857142858 -0,15117839559513543 mutant 1 
12319000 -109,59301470588237 -0,18277783185642743 mutant 1 
12319001 99,70264355742297 0,48329515727315125 mutant 2 
12319001 84,61113445378152 0,4060446341409862 mutant 2 

Tôi đã viết mã này:

oocytes = open(file_with_oocytes, 'r') 
results = open(os.path.join(path, 'results.csv'), 'r') 
results_new = open(os.path.join(path, 'results_with_oocytes.csv'), 'w') 
for line in results: 
    for lines in oocytes: 
     if lines[0:7] in line: 
      print line + lines[12:] 

Nhưng nó in ra này, và không có gì hơn, thow có 45 dòng trong tập tin đầu tiên:

 
12319000 99,4952380952381 0,3011778623990699 
    mutant 1 

12319000 99,4952380952381 0,3011778623990699 
    mutant 2 

12319000 99,4952380952381 0,3011778623990699 
    mutant 3 

Điều gì sai với mã? Hoặc nó nên được thực hiện bằng cách nào đó hoàn toàn khác nhau?

+7

+1 để bao gồm mã bạn đã thử – bernie

+0

Các tệp có theo thứ tự trên cột đầu tiên không? Đáng tin cậy như vậy? – MattH

+0

Các tệp có 'nhỏ' không? Tức là, họ có thể được đọc và giữ trong bộ nhớ cùng một lúc không? –

Trả lời

2

Lưu ý rằng giải pháp này không phụ thuộc vào độ dài của bất kỳ trường nào ngoại trừ độ dài của đuôi tệp trong tệp thứ hai.

# make a dict keyed on the filename before the extension 
# with the other two fields as its value 
file2dict = dict((row[0][:-4], row[1:]) 
        for row in (line.split() for line in file2)) 

# then add to the end of each row 
# the values to it's first column 
output = [row + file2dict[row[0]] for row in (line.split() for line in file1)] 

Đối với mục đích thử nghiệm mà thôi, tôi đã sử dụng:

# I just use this to emulate a file object, as iterating over it yields lines 
# just use file1 = open(whatever_the_filename_is_for_this_data) 
# and the rest of the program is the same 
file1 = """12319000 -64,7357668067227 -0,1111052148685535 
12319000 -79,68527661064425 -0,13231739777754026 
12319000 -94,69642857142858 -0,15117839559513543 
12319000 -109,59301470588237 -0,18277783185642743 
12319001 99,70264355742297 0,48329515727315125 
12319001 84,61113445378152 0,4060446341409862 
12319001 69,7032037815126 0,29803063228455073 
12319001 54,93886554621849 0,20958105041136763 
12319001 39,937394957983194 0,13623056582981297 
12319001 25,05574229691877 0,07748669438398018 
12319001 9,99716386554622 0,028110643107892755""".splitlines() 

# again, use file2 = open(whatever_the_filename_is_for_this_data) 
# and the rest of the program will work the same 
file2 = """12319000.abf mutant 1 
12319001.abf mutant 2 
12319002.abf mutant 3""".splitlines() 

nơi bạn chỉ nên sử dụng đối tượng tập tin bình thường. Đầu ra cho dữ liệu thử nghiệm là:

[['12319000', '-64,7357668067227', '-0,1111052148685535', 'mutant', '1'], 
    ['12319000', '-79,68527661064425', '-0,13231739777754026', 'mutant', '1'], 
    ['12319000', '-94,69642857142858', '-0,15117839559513543', 'mutant', '1'], 
    ['12319000', '-109,59301470588237', '-0,18277783185642743', 'mutant', '1'], 
    ['12319001', '99,70264355742297', '0,48329515727315125', 'mutant', '2'], 
    ['12319001', '84,61113445378152', '0,4060446341409862', 'mutant', '2'], 
    ['12319001', '69,7032037815126', '0,29803063228455073', 'mutant', '2'], 
    ['12319001', '54,93886554621849', '0,20958105041136763', 'mutant', '2'], 
    ['12319001', '39,937394957983194', '0,13623056582981297', 'mutant', '2'], 
    ['12319001', '25,05574229691877', '0,07748669438398018', 'mutant', '2'], 
    ['12319001', '9,99716386554622', '0,028110643107892755', 'mutant', '2']] 
+0

Tôi không hoàn toàn hiểu, làm thế nào điều này sẽ làm việc với các tập tin lỗ? Tôi nên sửa đổi phần đầu tiên là file1 = file1_old.splitlines() file2 = file2_old.splitlines() và sau đó thực hiện phần thứ hai? – Phlya

+1

@ Ilya Tôi đã thêm một vài nhận xét khác, nhưng về cơ bản chỉ sử dụng 'fileX = open (filename)' thay vì những gì tôi có cho tệp. – agf

+0

Cảm ơn bạn! Hãy thử ngay bây giờ. – Phlya

6

Xử lý tệp bằng Python có trạng thái; nghĩa là, chúng không hoạt động như danh sách. Bạn có thể lặp đi lặp lại lặp lại trên một danh sách và nhận được tất cả các giá trị mỗi lần. Các tập tin, mặt khác, có một vị trí mà từ đó read() tiếp theo sẽ xảy ra. Khi bạn lặp lại tệp, bạn có read() mỗi dòng. Khi bạn đến dòng cuối cùng, con trỏ tập tin nằm ở cuối tập tin. Một read() từ cuối tệp trả về chuỗi ''!

Những gì bạn cần làm là đọc trong oocytes tập tin một lần ngay từ đầu, và lưu trữ các giá trị, có lẽ một cái gì đó như thế này:

oodict = {} 
for line in oocytes: 
    oodict[line[0:7]] = line[12:] 

for line in results: 
    results_key = line[0:7] 
    if results_key in oodict: 
     print oodict[results_key] + line 
1

tốt, những điều đơn giản đầu tiên, bạn in các dòng mới vào cuối cùng của dòng - bạn sẽ muốn thả nó với dòng [0: -1]

Tiếp theo, "dòng [0: 7]" chỉ kiểm tra 7 ký tự đầu tiên của dòng - bạn muốn kiểm tra 8 ký tự. Đó là lý do tại sao cùng một giá trị của "dòng" được in ra với 3 giá trị đột biến khác nhau.

Cuối cùng, bạn cần phải đóng và mở lại oocytes cho mỗi dòng trong kết quả. Không làm như vậy đã kết thúc sản lượng của bạn sau dòng đầu tiên của kết quả.

Thực ra, câu trả lời khác tốt hơn - không mở và đóng oocytes cho mỗi dòng kết quả - mở nó và đọc nó trong danh sách một lần, sau đó lặp lại danh sách đó cho mỗi dòng kết quả.

+0

Tại sao lại gần và mở lại khi bạn chỉ có thể tìm kiếm (0)? –

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