Главная страница
Навигация по странице:

  • Глава Домашний психолог9

  • Несколько вопросов... 1. В чем разница между компонентами Label и Entry2. Как открыть и сохранить текстовые файлы с помощью программы...и задач

  • Меню для программы-психолога

  • Глава Меню и диалоговые окна10

  • Открыть и Сохранить

  • Открыть

  • Открыть и Сохра- нить

  • Готово

  • Выход

  • Шуман Х. - Python для детей - 2019. # Startwerte festlegen Red (255,0,0)


    Скачать 5.95 Mb.
    Название# Startwerte festlegen Red (255,0,0)
    Дата10.03.2023
    Размер5.95 Mb.
    Формат файлаpdf
    Имя файлаШуман Х. - Python для детей - 2019.pdf
    ТипДокументы
    #977830
    страница13 из 22
    1   ...   9   10   11   12   13   14   15   16   ...   22
    Глава
    Домашний психолог
    9
    180
    Функция close() является противоположностью open().
    Есть еще кое-что, что мы не рассматривали здесь: как быть, если файл не существует? Или его невозможно прочитать?
    Нельзя ли установить механизм защиты, чтобы программа не выходила из-за этого из строя?
    Для решения проблемы мы отступим от структуры, кото- рую использовали долгое время. Взгляни на следующий код исключения (⇒ psych4.py):
    def loadDiagnose() :
    global Max
    Nr = 0
    try :
    File = open("diagnose.txt", "r")
    for String in File :
    Diagnose.append(String.rstrip())
    Nr += 1
    Max = Nr ­ 1
    File.close()
    except :
    Diagnose.append("Что-то не так с файлом диагнозов")
    Сначала функция пытается открыть файл и прочитать данные (try); если это не удается (except), то она сообщает о проблеме с файлом.
    except :
    Diagnose.append("Что-то не так с файлом диагнозов")
    Чтобы проверить работу программы в такой ситуации, ты должен на время переименовать файл (рис. 9.4).

    Все вместе
    181
    Рис. 9.4.Программа вызвала исключение
    Все вместе
    Давай перейдем к общему листингу, который немного уве- личился (⇒ psych4.py):
    # Психолог from tkinter import *
    import random
    # Константы текста
    State = ["Ты сказал мне:", "Я говорю тебе:", "Диагноз:"]
    Diagnose = []
    Max = 0
    # Файловая функция def loadDiagnose() :
    global Max
    Nr = 0
    try :
    File = open("diagnose.txt", "r")
    for String in File :
    Diagnose.append(String.rstrip())
    Nr += 1
    Max = Nr ­ 1
    File.close()
    except :

    Глава
    Домашний психолог
    9
    182
    Diagnose.append("Что-то не так с файлом диагнозов")
    # Функция для события def button1Click() :
    Input.delete(0,"end")
    Answer.config(text="")
    def button2Click() :
    Nr = random.randint(0,Max)
    Answer.config(text=Diagnose[Nr])
    def scaleValue(event) :
    Nr = Slider.get()
    Answer.config(text=Diagnose[Nr])
    # Основная программа
    Window = Tk()
    Window.title("Психолог")
    Window.minsize(width=500, height=330)
    loadDiagnose()
    # Определение состояния
    Display = []
    Border = []
    for pos in range(0,3) :
    Display.append(Label(Window, text=State[pos]))
    Display[pos].place(x=20, y=10+pos*90, width=460, height=30)
    Border.append(Frame(Window, borderwidth=2, relief="groove"))
    Border[pos].place(x=20, y=40+pos*90, width=460, height=50)
    # Ввод, ответ и ползунковый регулятор
    Input = Entry(Border[0])
    Input.place(x=10, y=10, width=440, height=30)
    Answer = Label(Border[1])
    Answer.place(x=10, y=10, width=440, height=30)
    Slider = Scale(Border[2], orient="horizontal", command=scaleValue)
    Slider.config(from_=0, to=Max, length=430, showvalue=0)
    Slider.pack(pady=10)
    # Кнопки "Готово" и "Заново"
    Button1 = Button(Window, text="Заново", command=button1Click)
    Button1.place(x=120, y=285, width=120, height=30)
    Button2 = Button(Window, text="Готово", command=button2Click)
    Button2.place(x=260, y=285, width=120, height=30)
    # Цикл событий
    Window.mainloop()
    Как видишь, существенные изменения претерпела только верхняя часть исходного кода.
    ¾
    Измени код своей предыдущей версии программы и убедись, что у тебя есть текстовый файл с корректным

    Журнал диагностики
    183
    именем. Разумеется, ты можешь воспользоваться фай- лом с диагнозами из папки с примерами. Да начнется терапия!
    Ты действительно не понял, как работает программа?

    В поле ввода ты можешь ввести все, что хочешь. Тебе не нужно подбирать слова, потому что здесь нет цензуры.

    Затем нажми кнопку «Готово» и получи ответную фразу в объ- явлении под строкой «Я говорю тебе», что, конечно же, не всегда соответствует введенному тобой тексту. Но может быть, ответ подкинет тебе какую-то идею?

    Нажми кнопку «Заново», чтобы удалить свой текст из поля ввода, после чего ты можешь ввести что-то новое. Это может быть комментарий к диагнозу или что-то еще.

    Если ответы программы кажутся тебе неуместными, перетас- кивай ползунковый регулятор, чтобы найти более подходя- щий ответ.

    Если программа-психолог действует тебе на нервы, то ты зна- ешь, как завершить ее работу.
    Журнал диагностики
    Теперь ты узнаешь, как сохранить текст из программы в файл: мы немного расширим функционал нашего вирту- ального психолога. Для этого нам нужен еще один список:
    Psychosis = []
    Этот список должен собирать все, что ты скажешь психоло- гу посредством ввода текста, а в конце сеанса терапии со- хранить собранные данные в файл psychox.txt. Вместо сим- вола x ты также можешь использовать число, если хочешь сохранить текст в нескольких файлах. (Если ты придумал лучшее имя своему файлу, используй его!)
    Лучше всего собирать ответы вместе с вводимым тобой текстом. Но сначала мы должны создать и открыть соответ- ствующий файл:
    File = open("psychoX.txt", "w")
    Здесь используется режим "w", который является аббревиа- турой слова «write», запись. Файл создается в той же папке, где запускается текущая программа.

    Глава
    Домашний психолог
    9
    184
    Затем используется цикл, в котором считывается каждая строка:
    for String in Psychosis :
    File.write(String+"\n")
    К каждой строке в файле добавляется последовательность \n, чтобы каждое предложение размещалось в отдельной стро- ке. Если ты откроешь этот файл с помощью текстового редак- тора, то сможешь посмотреть его (и изменить, если нужно).
    Подобно функции write(), существует также метод чтения строк.
    Нам они не нужны в функции loadDiagnose(), где строки берутся непосредственно из файла.
    Можно также «обернуть объекты» функцией read(). Это громозд- кий метод, но ты наверняка встретишь такой способ, и не раз, по- этому стоит о нем упомянуть. Выглядит он так:
    String
    = file.read()
    Затем содержимое переменной String должно стать элементом ответа.
    Теперь функция saveDialog() выглядит следующим образом
    (⇒ psych5.py):
    def saveDiagnose() :
    try :
    File = open("psychoX.txt", "w")
    for String in Psychosis :
    File.write(String+"\n")
    File.close()
    ¾
    Дополни свою программу этой функцией. Ее лучше всего вставить непосредственно под определение load­
    Diagnose()
    . Не забудь о диагнозах в виде списка.
    Перейдем к функции события button2Click(). Вводимый текст и строки ответов должны вставляться в список диаг- нозов, а затем сохраняться. Так мы получаем дополненную версию программы (⇒ psych5.py):
    def button2Click() :
    Nr = random.randint(0,Max)
    Answer.config(text=Diagnose[Nr])
    Psychosis.append(Input.get())
    Psychosis.append(Diagnose[Nr])
    saveDiagnose()

    ...и задач
    185
    Измени свою программу. Теперь ты можешь запустить ее, а затем просмотреть, что находится в файле psychox.txt.
    Ты найдешь все файлы для программы-психолога в папке с при- мерами по адресу dmkpress.com
    Подведение итогов
    Мы совершили большой прорыв! Из-за обилия компонен- тов ты можешь не разглядеть важную часть исходного кода.
    Давай соберем в таблице то, что упоминается в главе:
    open()
    Открывает файл для записи ("w") или чтения ("r")
    close()
    Закрывает файл read()
    Считывает строковые данные write()
    Записывает строковые данные rstrip()
    Обрезает строку по указанным символам
    (по умолчанию \n – символ конца строки)
    Entry
    Поле ввода (для текста и цифр)
    delete()
    Удаляет ввод
    Scale
    Ползунковый регулятор для числовых значений orient=
    Отвечает за расположение ползункового регулятора по горизонтали или вертикали showvalue=
    Отвечает за отображение значения ползункового регулятора: да (1) или нет (0)
    relief=
    Оформление компонента рамкой: например, плоской, утопленной, выступающей, рельефной
    Несколько вопросов...
    1. В чем разница между компонентами Label и Entry?
    2. Как открыть и сохранить текстовые файлы с помощью программы?
    ...и задач
    1. Расширь функцию saveDiagnose() с помощью конструк- ции try­except.
    2. Создай программу, которая отображает значение от 0 до 100 %, изменяемое с помощью ползункового регуля- тора.

    186
    10
    Меню
    и диалоговые окна
    Возможность программы-психолога загружать и сохранять текст – это прекрасно. Но ты можешь открыть только кон- кретный файл и сохранить данные в определенный файл.
    Этого недостаточно.
    В этой главе мы расширим программу, реализовав то, что есть у многих других приложений: меню. Помимо всего, ты сможешь выбирать, какой файл ты хочешь открыть или под каким именем должен быть сохранен полученный диагноз.
    Итак, в этой главе ты узнаешь:
    
    как добавить в программу меню;
    
    как использовать диалоговые окна открытия и сохра- нения файлов;
    
    кое-что о контекстных меню и всплывающих окнах;
    
    подробнее о событиях;
    
    как использовать сочетания клавиш;
    
    как с удобством завершать работу программы.
    Меню для программы-психолога
    В первую очередь нам нужно меню, с помощью которого мы сможем открыть или сохранить файл.
    Однако мы не сможем обойтись одним компонентом, так как меню включает в себя не только команды меню, но так-

    Меню для программы­психолога
    187
    же саму строку меню. Необходимым компонентом, как ми- нимум, является Menu:
    Menuitem = Menu(Window)
    Window.config(menu=Menuitem)
    Filemenu = Menu(Menuitem)
    Но так ты ничего не увидишь, в строке меню должен по- явиться текст. Ты добавляешь его с помощью метода add_
    cascade()
    :
    Menuitem.add_cascade(label="Файл", menu=Filemenu)
    Параметр menu связывает пункт непосредственно с первым меню (с именем «Файл»).
    Выполнив эти инструкции, ты уже можешь увидеть некое подобие меню, как показано на рис. 10.1.
    Рис. 10.1.Первое меню для программы
    Прежде чем мы внесем все это в нашу программу, я хотел бы предложить тебе сделать небольшую дополнительную программу, в которой ты сможешь открыть меню и щелк- нуть по нему:
    from tkinter import *
    Window = Tk()
    Menuitem = Menu(Window)
    Window.config(menu=Menuitem)
    Filemenu = Menu(Menuitem)
    Menuitem.add_cascade(label="Файл", menu=Filemenu)

    Глава
    Меню и диалоговые окна
    10
    188
    Filemenu.add_command(label="Открыть_и_Сохранить'>Открыть")
    Filemenu.add_command(label="Сохранить")
    Filemenu.add_command(label="Выход")
    Helpmenu = Menu(Menuitem)
    Menuitem.add_cascade(label="Справка", menu=Helpmenu)
    Helpmenu.add_command(label="О программе")
    Window.mainloop()
    Функция add_cascade() отвечает за пункты в строке меню, а add_command() компилирует команды в меню.
    Первый запуск программы демонстрирует результат, пока- занный на рис. 10.2 (я открыл меню
    Файл).
    Рис. 10.2.Рабочее меню Файл
    Теперь ты можешь, по желанию, открыть или сохранить любой файл. А выбрав команду
    Выход, можешь закрыть программу. Здесь также есть меню
    Справка. Конечно, ты можешь выбрать его, но не увидишь никакого эффекта. Это тот результат, которого мы хотели достичь: у нас теперь есть система меню, встроенная в программу.
    Теперь, когда основная программа уже довольно сложная, лучше всего создать систему меню в виде отдельной функ- ции. Вот моя первая попытка:
    def initMenu() :
    Menuitem = Menu(Window)
    Window.config(menu=Menuitem)
    Filemenu = Menu(Menuitem, tearoff = 0)
    Menuitem.add_cascade(label="Файл", menu=Filemenu)

    Меню для программы­психолога
    189
    Filemenu.add_command(label="Открыть", command=openFile)
    Filemenu.add_command(label="Сохранить", command=saveFile)
    Filemenu.add_command(label="Выход", command=closeAll)
    Helpmenu = Menu(Menuitem, tearoff = 0)
    Menuitem.add_cascade(label="Справка", menu=Helpmenu)
    Helpmenu.add_command(label="О программе")
    Обрати внимание, два пункта строки меню имеют пара- метр tearoff = 0. Он удаляет довольно уродливую, с моей точки зрения, пунктирную линию в меню. Также я подго- товил несколько методов command для команд в меню
    Файл, но пока они не работают.
    Основной код программы требует внесения дополнитель- ной строки (⇒ psych6.py):
    initMenu()
    ¾
    Дополни код последней версии программы-психолога новой функцией и вызови ее, а затем запусти програм- му. Выбирай пункты меню и проверь, все ли команды работают (рис. 10.3).
    Рис. 10.3.Версия программы с меню

    Глава
    Меню и диалоговые окна
    10
    190
    Два диалоговых окна
    Теперь нам понадобятся дополнительные функции собы- тий. Давай проработаем команды
    Открыть и Сохранить.
    Чего бы нам хотелось?

    Чтобы в открывшемся диалоговом окне мы могли вы- брать текстовый файл. Затем этот файл можно было бы загрузить.

    Чтобы при сохранении можно было ввести имя в диа- логовом окне. Затем файл должен быть сохранен.
    Звучит как что-то сложное, но не в случае с библиотекой tkinter
    . У нее есть что предложить – модуль filedialog, кото- рый может выполнить часть работы за нас. askopenfilename() и asksaveasfilename() – еще два хороших вспомогательных метода.
    Для этого сначала нужно добавить еще одну строку import в верхней части исходного кода:
    from tkinter import filedialog
    Даже если указать символ звездочки, с помощью которой импортируются все классы модуля, этого недостаточно, filedialog нужны «особенные привилегии».
    Давай посмотрим, что происходит, когда ты выбираешь один из пунктов меню –
    Открыть или Сохранить. Ниже представлены две функции события (⇒ psych6.py):
    def openFile() :
    Name = filedialog.askopenfilename(filetypes= \
    (("Текстовые файлы","*.txt"),("Все файлы","*.*")))
    if Name != "":
    Diagnose.clear()
    loadDiagnose(Name)
    Slider.config(to=Max) def saveFile() :
    Name = filedialog.asksaveasfilename()
    if Name != "":
    saveDiagnose(Name)
    Сначала функция openFile() открывает диалоговое окно, показанное на рис. 10.4, в котором ты можешь выбрать имя файла или ввести его. Это достигается с помощью метода askopenfilename()
    . В качестве параметров ты можешь указать определенные пара метры по умолчанию.

    Два диалоговых окна
    191
    С помощью параметра filetypes ты определяешь, файлы с какими расширениями будут отображаться. Я указал текс- товые файлы (txt), но есть также вариант
    Все файлы.
    Если имя выбрано, текущий диагноз удаляется, а затем за- гружается содержимое нового файла. Но если выбор отме- нен, name!="" и все прочее остается без изменений. Важно, чтобы после успешного завершения загрузки ползунковый регулятор подгонялся под количество строк текста в новом файле.
    Рис. 10.4.Диалоговое окно открытия файла
    При сохранении открывается диалоговое окно, в котором ты можешь указать имя, под которым хочешь сохранить файл. Это делается с помощью метода requestaveasfilename(), тогда файл можно сохранить, только если имя указано.
    Поскольку параметры файлов с диагнозами больше не определяются однозначно командами
    Открыть и Сохра-
    нить, две файловые функции теперь имеют соответствую- щий параметр (⇒ psych6.py):
    def loadDiagnose(Name) :
    def saveDiagnose(Name) :
    Внутри двух функций вызов метода open() должен быть на- строен так, чтобы он принимал общее имя файла:
    File = open(Name, "r")
    File = open(Name, "w")

    Глава
    Меню и диалоговые окна
    10
    192
    По желанию ты можешь оставить методы loadDiagnose() и saveDiagnos() в программе, но теперь добавь по одному параметру в каждую функцию:
    loadDiagnose("diagnose.txt")
    saveDiagnose("psychoX.txt")
    Этот код загрузит стандартный файл в начале, затем нажми кнопку
    Готово, чтобы сохранить сеанс в файл с именем по умолчанию. Все как раньше. Но если ты воспользуешься меню, то сможешь обойти дефолтное поведение.
    Последняя команда в меню
    Файл должна также иметь функцию события:
    def closeAll() :
    Window.destroy()
    Как только ты выбрал команду
    Выход, окно и его содержи- мое удаляются с помощью метода troythe(), таким образом завершая работу tkinter-программы.
    Полный исходный код
    Теперь соберем полный исходный код новой версии про- граммы-психолога. Внеси изменения в свой файл, а затем запусти программу (⇒ psych6.py):
    # Психолог from tkinter import *
    from tkinter import filedialog import random
    # Константы текста
    State = ["Ты сказал мне:", "Я говорю тебе:", "Диагноз:"]
    Diagnose = []
    Psychosis = []
    Max = 0
    # Функции меню def initMenu() :
    Menuitem = Menu(Window)
    Window.config(menu=Menuitem)
    Filemenu = Menu(Menuitem, tearoff = 0)
    Menuitem.add_cascade(label="Файл", menu=Filemenu)
    Filemenu.add_command(label="Открыть", command=openFile)
    Filemenu.add_command(label="Сохранить", command=saveFile)

    Полный исходный код
    193
    Filemenu.add_command(label="Выход", command=closeAll)
    Helpmenu = Menu(Menuitem, tearoff = 0)
    Menuitem.add_cascade(label="Справка", menu=Helpmenu)
    Helpmenu.add_command(label="О программе")
    # Файловые функции def loadDiagnose(Name) :
    global Max
    Nr = 0
    try :
    File = open(Name, "r")
    for String in File :
    Diagnose.append(String.rstrip())
    Nr += 1
    Max = Nr ­ 1
    File.close()
    except :
    Diagnose.append("Что-то не так с файлом диагнозов")
    def saveDiagnose(Name) :
    try :
    File = open(Name, "w")
    for String in Psychosis :
    File.write(String+"\n")
    File.close()
    except :
    print("Не получается сохранить файл")
    # Функция для события def button1Click() :
    Input.delete(0,"end")
    Answer.config(text="")
    def button2Click() :
    Nr = random.randint(0,Max)
    Answer.config(text=Diagnose[Nr])
    Psychosis.append(Input.get())
    Psychosis.append(Diagnose[Nr])
    saveDiagnose("psychoX.txt") def scaleValue(event) :
    Nr = Slider.get()
    Answer.config(text=Diagnose[Nr])
    # Команды меню def openFile() :
    Name = filedialog.askopenfilename(filetypes= \
    (("Текстовые файлы","*.txt"),("Все файлы","*.*")))
    if Name != "":
    Diagnose.clear()
    loadDiagnose(Name)
    Slider.config(to=Max) def saveFile() :
    Name = filedialog.asksaveasfilename()

    1   ...   9   10   11   12   13   14   15   16   ...   22


    написать администратору сайта