Сценарий Python, создающий карточки anki с использованием genanki (ожидаемый экземпляр str, dict found ERROR)
Программа берет список английских слов, записанных в первом столбце файла Excel с именем "Список", используя панд, заголовок столбца - "слова", а слова находятся в "Листе 1".
Слова затем сохраняются в виде списка строк.
PyDictionary и Googletrans используются при создании словаря и переводчика, где переводчик вызывается переводчиками, чтобы перевести слова из списка на целевой язык "датский".
Затем создается простой цикл for, где каждый перевод в списке переведенных слов печатается с его происхождением -> местом назначения и определением.
Это представлено в коде ниже:
from googletrans import Translator
import pandas as pd
from PyDictionary import PyDictionary
# Load excel file and parse the list of words as strings
file_location = "/Users/.../List.xlsx"
xl_workbook = pd.ExcelFile(file_location)
df = xl_workbook.parse("Sheet1")
aList = df['words'].tolist()
[str(i) for i in aList]
# Use PyDictionary to load definitions of words
dictionary = PyDictionary()
# Translate the list of strings into target language and give definitions
translator = Translator()
translations = translator.translate(aList, dest='da')
# Simple for-loop printing the words
for translation in translations:
print(
translation.origin, ' -> ', translation.text,
dictionary.meaning(translation.origin)
)
Эта программа на самом деле работает и дал желаемый результат. Однако проблема возникает на следующем шаге, как описано здесь:
Я хочу ввести слова в мою любимую флеш-программу Anki. Anki написана на Python и имеет неофициальный дистрибутив Genanki. Тем не менее, это когда я сталкиваюсь с моими проблемами.
Теперь я добавлю следующие 4 вещи в мой код выше:
- Я определяю my_model в соответствии с предложением genanki и создаю простую модель карточки. Это включает в себя случайное жестко закодированное число (которое требует Anki), название модели, некоторые поля и шаблон для типа карты.
- Я определяю my_deck как определенную колоду карточек с жестко закодированным случайным числом и именем.
- Я изменяю цикл for, чтобы теперь запускать переводы и определения непосредственно в переменную с именем aNote, которая состоит из оператора genanki.note, выполняющего итерации переводов каждый раз, добавляя заметку в my_deck.
- Я пишу свой anki-файл, который я могу открыть с помощью Anki.
Это можно увидеть в коде ниже:
from googletrans import Translator
import pandas as pd
from PyDictionary import PyDictionary
import genanki
# Load excel file and parse the list of words as strings
file_location = "/Users/.../List.xlsx"
xl_workbook = pd.ExcelFile(file_location)
df = xl_workbook.parse("Sheet1")
aList = df['words'].tolist()
[str(i) for i in aList]
# Use PyDictionary to load definitions of words
dictionary = PyDictionary()
# Use genanki to define a flashcard model
my_model = genanki.Model(
2042686211,
'Simple Model',
fields=[
{'name': 'Question'},
{'name': 'Answer'},
],
templates=[
{
'name': 'Card 1',
'qfmt': '{{Question}}',
'afmt': '{{FrontSide}}<hr id="answer">{{Answer}}',
},
])
# Specify the deck with genanki
my_deck = genanki.Deck(
1724897887,
'TestV3v1')
# Translate the list of strings with definition and add as note to anki
translator = Translator()
translations = translator.translate(aList, dest='da')
for translation in translations:
aNote = genanki.Note(
model=my_model, fields=[translation.origin, translation.text]
)
my_deck.add_note(aNote)
# Output anki file in desired folder
genanki.Package(my_deck).write_to_file(
'/Users/.../TestV3v1.apkg')
Этот код также выполняется очень хорошо и генерирует файл, который можно открыть в Anki, карта затем показывает оригинальное слово на передней части карточки с переводом на обратной стороне.
Моя проблема
Чтобы завершить свой проект, я хочу добавить определение на обороте каждой карточки, сопровождающей перевод. Первоначально я думал, что мне просто нужно исправить переменную my_model = genanki.model (...), добавив другое поле, чтобы я мог просто добавить dictionary.meaning (translation.origin) к генератору заметок в цикле for,
Однако, пытаясь добавить только определения, чтобы убедиться, что они работают без сбоев, я сталкиваюсь с проблемами. Рассмотрим код ниже:
for translation in translations:
aNote = genanki.Note(
model=my_model, fields=[translation.origin,
dictionary.meaning(translation.origin)
]
)
my_deck.add_note(aNote)
Я ожидал, что карточки будут напечатаны как обычно, с оригинальным словом на передней стороне и определением на обратной стороне, но вместо этого полный код с этим циклом for дает мне следующие ошибки:
Error: The Following Error occured: list index out of range
Error: The Following Error occured: list index out of range
Error: The Following Error occured: list index out of range
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: The Following Error occured: list index out of range
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: The Following Error occured: list index out of range
Error: The Following Error occured: list index out of range
Error: The Following Error occured: list index out of range
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: A Term must be only a single word
Error: The Following Error occured: list index out of range
Error: A Term must be only a single word
Error: The Following Error occured: list index out of range
Traceback (most recent call last):
File "/Users/Lehmann/Desktop/XYZ/Programming/Translator/TranslatorProgramv3.py", line 51, in <module>
'/Users/Lehmann/Desktop/XYZ/Programming/Translator/TestV3v1.apkg')
File "/anaconda3/lib/python3.6/site-packages/genanki/__init__.py", line 313, in write_to_file
self.write_to_db(cursor, now_ts)
File "/anaconda3/lib/python3.6/site-packages/genanki/__init__.py", line 331, in write_to_db
deck.write_to_db(cursor, now_ts)
File "/anaconda3/lib/python3.6/site-packages/genanki/__init__.py", line 267, in write_to_db
note.write_to_db(cursor, now_ts, self.deck_id)
File "/anaconda3/lib/python3.6/site-packages/genanki/__init__.py", line 228, in write_to_db
self._format_fields(), # flds
File "/anaconda3/lib/python3.6/site-packages/genanki/__init__.py", line 240, in _format_fields
return '\x1f'.join(self.fields)
TypeError: sequence item 1: expected str instance, dict found
Я подозреваю, что именно часть "Ожидаемый экземпляр, найденный dict" доставляет мне неприятности, однако это мой самый первый проект на Python, и я не программист, поэтому я надеюсь, что кто-то там поможет мне разобраться в проблеме.
BR
Миккель
1 ответ
Всегда проверяйте тип переменной, когда вы ее используете. Из того, что я нашел, использование dictionary.meaning(...) меняет тип на словарь. Так что все, что вам нужно сделать, это:
meaning=dictionary.meaning(translation.origin)
meaning_to_string=''.join('{}: {}'.format(key,val) for key,val in meaning.items())
#moving to aNote
aNote=genanki.Note(model=my_model, fields=[translation.origin,meaning_to_string])