2016-10-26 5 views
1

Я только начал питон и у меня есть около 6000 .txt файлов каждый из которых содержит несколько номеров, в колонке, как:Читать номера из многих текстовых файлов и усреднить их Python

file1.txt:

2

43

78

file2.txt:

98

12

and so on 

Я хочу, чтобы прочитать их и хранить их в массив и вычислить его среднее значение. Среднего значение (2,43,78,98,12 ..) т.е. все числа из всех файлов должны дать 1 вид Когда я читаю и хранить их, как они выглядят:

['2, 43, 78', '98, 12',..]

... (I избавился от «\ n») Но когда я использую ave = sum(a)\float(len(a)), я получаю сообщение об ошибке. Что я делаю неправильно? Есть ли что-нибудь, что я пропустил, или еще один способ сделать это?

Код:

import fnmatch 
import os 

rootPath = 'D:/Data' 
pattern = '*.txt' 
all_data = [] 
for root, dirs, files in os.walk(rootPath): 
    for filename in fnmatch.filter(files, pattern): 
     #print(filename) 
     name = os.path.join(root, filename) 
     str = open(name, 'r').read() 
     #print str 
     all_data.append(str) 
a=[item.replace('\n', ' ') for item in all_data] 
#print a 
for val in a: 
    values = map(float, val.split(", ")) 
    ave = sum(values)/len(values) 
    print ave 

Я получаю сообщение об ошибке:

invalid literal for float()

+6

, пожалуйста, введите код и данные об ошибке –

+0

строки - это не номера, которые вам нужны для запуска их (а не их длина, что является нечетным выбором) один за другим через 'float()' –

+0

@Iabmat: Вам нужно иметь в виду каждый файл отдельно или все файлы? –

ответ

3

sum("abc") не определен. Также нет sum("2, 43"). sum работает только с числовыми типами.

Вам нужно разделить линию первого и преобразовать значения в числовое значение (я использовал float здесь, потому что тогда sum будет float, поэтому нет необходимости конвертировать len в float):

rows = ['2 43 78', '98 12'] 
total_sum = total_len = 0 
for row in rows: 
    values = map(float, row.split()) 
    total_sum += sum(values) 
    total_len += len(values) 
print total_sum/total_len 

для Python 3.x заменить print avg с print(avg) и добавить list() вокруг map, потому что в противном случае len не определен для него.

Это похоже на то, что @VadimK имеет в his answer, но избегает добавления списка и просто добавляет целое число.

+0

Это работал как на моих тестовых, так и на реальных данных! Большое вам спасибо :) – labmat

2

Простой подход с использованием список понимание как:

>>> my_list = ['2, 43, 78', '98, 12'] 
>>> my_nums = [float(j) for i in my_list for j in i.split(', ')] 
>>> avg = sum(my_nums)/float(len(my_nums)) 
>>> avg 
46.6 
+0

Спасибо за это! Когда я пытаюсь это сделать, как вы опубликовали, я получаю правильный ответ, но по моим данным я получаю: недопустимый литерал для float() – labmat

1

Я думаю, что может быть лучше, чтобы отображать номера после чтения файла как:

total_list = [] 
for file in files: 
    str_list = file.read().splitlines() # ['1', '2', '3', '4', '5', '6'] 
    int_list = map(int, str_list) # [1, 2, 3, 4, 5, 6] 
    total_list += int_list 
ave = sum(total_list)/float(len(total_list)) 
0

Простой метод с использованием glob для Linux

import glob 
tot_list=[] 
for i in glob.glob('*.txt'):  #Return a list of .txt files in current directory 
# print('file:', i) 
    with open(i) as f:    #Open file, read lines 
     lines = f.readlines() 
     for x in lines:    # process each line 
      try: 
       x=int(x)   #Test for integer value 
       tot_list.append(x) #Include in list 
      except: 
       pass 
print('Total:',sum(tot_list),'No of Items:',len(tot_list)) 
print('Mean : %.2f' % (sum(tot_list)*1.0/len(tot_list))) #Print floating point result to 2 decimal places 
Смежные вопросы