Как объединить Cmd и Matplotlib в python

Я хотел бы объединить интерактивный график в Matplotlib и интерфейс командной строки Cmd в python. Как я могу это сделать? Могу ли я использовать резьбу? Я пробовал следующее:

from cmd import Cmd
import matplotlib.pylab as plt
from threading import Thread

class MyCmd(Cmd):

    def __init__(self):
        Cmd.__init__(self)
        self.fig = plt.figure()
        self.ax = self.fig.add_subplot(1,1,1)

    def do_foo(self, arg):
        self.ax.plot(range(10))
        self.fig.canvas.draw()

if __name__=='__main__':
    c = MyCmd()
    Thread(target=c.cmdloop).start()
    plt.show()

Он открывает окно рисунка, и я могу вводить команды в консоли, которые фактически выполняются. Когда выполняется команда "foo", она рисует в окне рисунка. Пока все в порядке. Однако, когда я снова вхожу в консоль, консоль кажется зависшей, и теперь появляется новое командное окно. Но когда я нажимаю на окно рисунка, консоль выводит новую командную строку, и я могу ввести новую команду. Кажется, две петли на самом деле не чередуются или что-то в этом роде. Есть ли лучший, более распространенный способ?


person Christian    schedule 12.08.2010    source источник
comment
Пожалуйста, отредактируйте свой вопрос. При редактировании читайте инструкции по форматированию в правой части страницы. Пожалуйста, отредактируйте свой код, чтобы он выглядел как code.   -  person S.Lott    schedule 13.08.2010
comment
Как это не работает? Какую версию Python вы используете? Какая платформа? Как определяется Thread (похоже, вы его не импортируете)?   -  person robert    schedule 13.08.2010
comment
Я использую Python 2.6 в Linux.   -  person Christian    schedule 13.08.2010


Ответы (2)


Я нашел что-то, что работает, но довольно уродливо

from cmd import Cmd
import matplotlib.pylab as plt
from threading import Thread
import time

class MyCmd(Cmd):

    def __init__(self):
        Cmd.__init__(self)
        self.fig = plt.figure()
        self.ax = self.fig.add_subplot(1,1,1)

    def do_foo(self, arg):
        self.ax.plot(range(10))
        self.fig.canvas.draw()

if __name__=='__main__':
    plt.ion()
    c = MyCmd()
    def loop():
        while True:
            c.fig.canvas.draw()
            time.sleep(0.1)
    Thread(target=loop).start()
    c.cmdloop()

Это просто периодически вызывает метод рисования фигуры. Если я этого не сделаю, фигура не перерисовывается, когда она была закрыта, и снова выходит на передний план.

Но это кажется некрасивым. Есть ли способ лучше?

person Christian    schedule 13.08.2010

iPython довольно популярен. Взгляните на Использование matplotlib в оболочке Python.

person user500198    schedule 08.11.2010