我不能使用任何匯入的庫。我有這個任務,我有一些包含一些檔案的目錄;每個檔案的第一行除了一些單詞外,還包含要打開的下一個檔案的名稱。一旦打開目錄中包含的每個檔案的每個單詞,就必須以應該回傳單個字串的方式處理它們;這樣的字串在其第一個位置包含之前出現的每個單詞的最常見的第一個字母,在其第二個位置包含最常見的第二個字母,依此類推。我已經設法用一個包含 3 個檔案的目錄來做到這一點,但它沒有使用任何型別的類似鏈的機制,而是傳遞區域變數。我的一些大學同事建議我必須使用串列切片,但我不知道如何使用。我不能使用任何匯入的庫。這就是我得到的:
'''
The objective of the homework assignment is to design and implement a function
that reads some strings contained in a series of files and generates a new
string from all the strings read.
The strings to be read are contained in several files, linked together to
form a closed chain. The first string in each file is the name of another
file that belongs to the chain: starting from any file and following the
chain, you always return to the starting file.
Example: the first line of file "A.txt" is "B.txt," the first line of file
"B.txt" is "C.txt," and the first line of "C.txt" is "A.txt," forming the
chain "A.txt"-"B.txt"-"C.txt".
In addition to the string with the name of the next file, each file also
contains other strings separated by spaces, tabs, or carriage return
characters. The function must read all the strings in the files in the chain
and construct the string obtained by concatenating the characters with the
highest frequency in each position. That is, in the string to be constructed,
at position p, there will be the character with the highest frequency at
position p of each string read from the files. In the case where there are
multiple characters with the same frequency, consider the alphabetical order.
The generated string has a length equal to the maximum length of the strings
read from the files.
Therefore, you must write a function that takes as input a string "filename"
representing the name of a file and returns a string.
The function must construct the string according to the directions outlined
above and return the constructed string.
Example: if the contents of the three files A.txt, B.txt, and C.txt in the
directory test01 are as follows
test01/A.txt test01/B.txt test01/C.txt
-------------------------------------------------------------------------------
test01/B.txt test01/C.txt test01/A.txt
house home kite
garden park hello
kitchen affair portrait
balloon angel
surfing
the function most_frequent_chars ("test01/A.txt") will return "hareennt".
'''
def file_names_list(filename):
intermezzo = []
lista_file = []
a_file = open(filename)
lines = a_file.readlines()
for line in lines:
intermezzo.extend(line.split())
del intermezzo[1:]
lista_file.append(intermezzo[0])
intermezzo.pop(0)
return lista_file
def words_list(filename):
lista_file = []
a_file = open(filename)
lines = a_file.readlines()[1:]
for line in lines:
lista_file.extend(line.split())
return lista_file
def stuff_list(filename):
file_list = file_names_list(filename)
the_rest = words_list(filename)
second_file_name = file_names_list(file_list[0])
the_lists = words_list(file_list[0]) and
words_list(second_file_name[0])
the_rest = the_lists[0:]
return the_rest
def most_frequent_chars(filename):
huge_words_list = stuff_list(filename)
maxOccurs = ""
list_of_chars = []
for i in range(len(max(huge_words_list, key=len))):
for item in huge_words_list:
try:
list_of_chars.append(item[i])
except IndexError:
pass
maxOccurs = max(sorted(set(list_of_chars)), key = list_of_chars.count)
list_of_chars.clear()
return maxOccurs
print(most_frequent_chars("test01/A.txt"))
uj5u.com熱心網友回復:
如果代碼具有良好的結構,則此分配相對容易。這是一個完整的實作:
def read_file(fname):
with open(fname, 'r') as f:
return list(filter(None, [y.rstrip(' \n').lstrip(' ') for x in f for y in x.split()]))
def read_chain(fname):
seen = set()
new = fname
result = []
while not new in seen:
A = read_file(new)
seen.add(new)
new, words = A[0], A[1:]
result.extend(words)
return result
def most_frequent_chars (fname):
all_words = read_chain(fname)
result = []
for i in range(max(map(len,all_words))):
chars = [word[i] for word in all_words if i<len(word)]
result.append(max(sorted(set(chars)), key = chars.count))
return ''.join(result)
print(most_frequent_chars("test01/A.txt"))
# output: "hareennt"
在上面的代碼中,我們定義了 3 個函式:
read_file: 讀取檔案內容并回傳字串串列的簡單函式。該命令x.split()會處理用于分隔單詞的任何空格或制表符。最后一條命令list(filter(None, arr))確保從解決方案中洗掉空字串。read_chain: 遍歷檔案鏈并回傳其中包含的所有單詞的簡單例程。most_frequent_chars:簡單的例程,其中最常見的字符被仔細計算。
附言。您的這行代碼非常有趣:
maxOccurs = max(sorted(set(list_of_chars)), key = list_of_chars.count)
我編輯了我的代碼以包含它。
空間復雜度優化
如果掃描檔案而不存盤所有單詞,則可以將前面代碼的空間復雜度提高幾個數量級:
def scan_file(fname, database):
with open(fname, 'r') as f:
next_file = None
for x in f:
for y in x.split():
if next_file is None:
next_file = y
else:
for i,c in enumerate(y):
while len(database) <= i:
database.append({})
if c in database[i]:
database[i][c] = 1
else:
database[i][c] = 1
return next_file
def most_frequent_chars (fname):
database = []
seen = set()
new = fname
while not new in seen:
seen.add(new)
new = scan_file(new, database)
return ''.join(max(sorted(d.keys()),key=d.get) for d in database)
print(most_frequent_chars("test01/A.txt"))
# output: "hareennt"
現在我們掃描檔案跟蹤 中字符的頻率database,而不存盤中間陣列。
uj5u.com熱心網友回復:
好的,這是我的解決方案:
def parsi_file(filename):
visited_files = set()
words_list = []
# Getting words from all files
while filename not in visited_files:
visited_files.add(filename)
with open(filename) as f:
filename = f.readline().strip()
words_list = [line.strip() for line in f.readlines()]
# Creating dictionaries of letters:count for each index
letters_dicts = []
for word in words_list:
for i in range(len(word)):
if i > len(letters_dicts)-1:
letters_dicts.append({})
letter = word[i]
if letters_dicts[i].get(letter):
letters_dicts[i][letter] = 1
else:
letters_dicts[i][letter] = 1
# Sorting dicts and getting the "best" letter
code = ""
for dic in letters_dicts:
sorted_letters = sorted(dic, key = lambda letter: (-dic[letter],letter))
code = sorted_letters[0]
return code
- 我們首先從所有檔案中獲取 words_list。
- 然后,對于每個索引,我們創建一個包含該索引處所有單詞中的字母及其計數的字典。
- 現在我們按降序計數 (-count) 然后按字母順序對字典鍵進行排序。
- 最后,我們得到第一個字母(因此具有最大計數的字母)并將其添加到此測驗電池的“代碼”字中。
編輯:就效率而言,隨著單詞數量的增加,為每個索引決議所有單詞會變得更糟,因此最好調整代碼以同時為每個索引創建詞典并僅決議一次單詞串列. 完畢。
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/536331.html
上一篇:在C中建立統計程序的問題
