diff --git a/.gitignore b/.gitignore index 9a9ac1c..60d068f 100644 --- a/.gitignore +++ b/.gitignore @@ -1,8 +1,10 @@ -*.aux -*.log -*.nav -*.out -*.pdf -*.snm -*.toc -*.vrb +/*.aux +/*.log +/*.nav +/*.out +/*.pdf +/*.snm +/*.toc +/*.vrb +*.pyc +*.pyo diff --git a/debugging_python.pdfpc b/debugging_python.pdfpc index b29611c..071b349 100644 --- a/debugging_python.pdfpc +++ b/debugging_python.pdfpc @@ -11,25 +11,19 @@ debugging_python.pdf · I w ostatniej części zaprezentuję przykładową sesję z debuggerem pdb ### 5 -· W przypadku gdy program zakończy się niepowodzeniem, jest spora szansa że wystąpi wyjątek: - np TypeError, IndexError, czy AttributeError +· W przypadku gdy program zakończy się niepowodzeniem, jest spora szansa że wystąpi wyjątek + - TypeError, IndexError, czy AttributeError - wynikiem tego jest traceback. Dzięki czemu jesteśmy w stanie stosunkowo prosto namierzyć miejsce w kodzie w którym nastąpił wyjątek + wynikiem tego jest traceback. Dzięki czemu jesteśmy w stanie stosunkowo prosto namierzyć miejsce w kodzie w którym nastąpił wyjątek. -· Jest to jeden z najprostszych sposobów na pokazanie wartości zmiennych w działającym nieprawidłowo programie, który nie rzuca wyjątkami. Jednocześnie jest on jednym z powszechniejszych wśród wszystkich języków programowania. -asd -· -· -· -· -· -· -· -· -· +· Wykorzystanie instrukcji print jest jednym z najprostszych sposobów na pokazanie wartości zmiennych w działającym (nieprawidłowo) programie, w przypadku gdy wykonanie programu nie kończy się rzuceniem wyjątku. Technika wypisywania na ekran informacji o stanie programu jest jedną z powszechniej stosowanych technik niezależnie od języka programowania. + +· moduł logging który dostarcza funkcjonalność logowania jest rozwinięciem powyższej metody - oprócz możliwości wypisywania informacji na ekran (konsolę) pozwala zdefiniować inne sposoby przesłania informacji o zdarzeniu - od wspomnianego wcześniej wypisywania na konsolę, po zapis do pliku lub wysłaniu do sysloga, a nawet do pokuszenia się o napisanie własnej obsługi +· moduł trace pozwala na sprawdzenie w jaki sposób przebiegło wykonanie naszego programu co pomoże w ustaleniu w którym miejscu coś poszło nie tak +· no i debugger - czyli program pozwalający na krokowe wykonanie programu, podglądu wartości zmiennych w danej chwili, zatrzymywaniem się we wskazywanych przez użytkownika miejscach, introspekcji (czasami) ### 7 ### 8 ### 9 -moduł logging który dostarcza funkcjonalność logowania jest rozwinięciem powyższej metody - oprócz możliwości wypisywania informacji na ekran (konsolę) pozwala zdefiniować inne sposoby przesłania informacji o zdarzeniu - od wspomnianego wcześniej wypisywania na konsolę, po zapis do pliku lub wysłaniu do sysloga, a nawet do pokuszenia się o napisanie własnej obsługi + diff --git a/debugging_python.tex b/debugging_python.tex index b1b0197..4b8161e 100644 --- a/debugging_python.tex +++ b/debugging_python.tex @@ -10,6 +10,8 @@ \usenavigationsymbolstemplate{} % Gets rid of slide navigation symbols \usefonttheme{professionalfonts} % using non standard fonts for beamer +% for proper underline +\usepackage[normalem]{ulem} \usepackage{fontspec} \defaultfontfeatures{Ligatures=TeX} @@ -39,8 +41,7 @@ \usepackage{graphicx} % \usepackage{sidecap} -\usepackage{hyperref} - +% \usepackage{hyperref} \usepackage{listings} @@ -125,7 +126,7 @@ \end{figure} } \only<2>{\begin{figure}[!htbp] - \includegraphics[width=3cm]{images/debugs2.png} + \includegraphics[width=3cm]{images/debugs.png} \end{figure} } \only<3>{\begin{figure}[!htbp] @@ -160,13 +161,62 @@ \endgroup \begin{frame} + Debuggers can be divided in several different aspects + \begin{columns} \column{.5\textwidth} - TBD + \begin{itemize}[<+->] + \item<1,2,3> Text based + \item<2,3> Graphical + \item<3> Embedded in IDE/editor + \end{itemize} \column{.4\textwidth} \end{columns} \end{frame} +\begin{frame} + \frametitle{Debuggers - text based} + \begin{columns} + \column{.4\textwidth} + \begin{itemize} + \item \lstinline{pdb} + \item \lstinline{ipdb} + \item \lstinline{ripdb} + \item \lstinline{pdb++} + \item \lstinline{pupdb} + \item \color{blue}\href{https://wiki.python.org/moin/PythonDebuggingTools}{\uline{others}} + \end{itemize} + \column{.5\textwidth} + \end{columns} +\end{frame} + +\begin{frame} + \frametitle{Debuggers - graphical} + \begin{columns} + \column{.4\textwidth} + \begin{itemize} + \item Winpdb + \item \lstinline{pywin.debugger} + \end{itemize} + \column{.5\textwidth} + \end{columns} +\end{frame} + +\begin{frame} + \frametitle{Debuggers - IDE/editors} + \begin{columns} + \column{.4\textwidth} + \begin{itemize} + \item PyCharm + \item PyDev (Eclipse) + \item Wings IDE + \item Visual Studio + \item \color{blue}\href{https://wiki.python.org/moin/IntegratedDevelopmentEnvironments}{\uline{others!}} + \end{itemize} + \column{.5\textwidth} + \end{columns} +\end{frame} + \begingroup \setbeamercolor{background canvas}{bg=ExecusharesBlack} \section{Python debugger - pdb} diff --git a/example/cm2inch.py b/example/cm2inch.py new file mode 100644 index 0000000..f5c8c3f --- /dev/null +++ b/example/cm2inch.py @@ -0,0 +1,102 @@ +import Tkinter as tk +import ttk + + +class CmInchConverter(object): + """Simple conversion between length in cm to inch and inch to cm""" + + def __init__(self): + """Initialize""" + self._root = None + self.value = "0" + self.result = "0" + self.convert_to_inches = None + + def run(self): + """Create and execute program""" + self._gui_initialize() + self._root.mainloop() + + def _gui_initialize(self): + """Initialize the GUI""" + self._root = tk.Tk() + self._root.title("inch/cm converter") + + self.convert_to_inches = tk.IntVar() + self.value = tk.StringVar() + self.result = tk.StringVar() + self.convert_to_inches.set(1) + self.value.set("0") + self.result.set("0") + + mainframe = ttk.Frame(self._root, padding="3 3 12 12") + mainframe.grid(column=0, row=0, sticky=(tk.N, tk.W, tk.E, tk.S)) + mainframe.columnconfigure(0, weight=1) + mainframe.rowconfigure(0, weight=1) + + defaults = {"padx": 2, "pady": 2, "sticky": tk.W} + + radio1 = tk.Radiobutton(mainframe, + text="cm to inches", + padx=2, + variable=self.convert_to_inches, + value=1) + radio1.grid(column=0, row=2, columnspan=2, **defaults) + radio2 = tk.Radiobutton(mainframe, + text="inches to cm", + padx=2, + variable=self.convert_to_inches, + value=2) + radio2.grid(column=0, row=3, columnspan=2, **defaults) + + ttk.Label(mainframe, text="Enter value:").grid(column=0, row=1, + **defaults) + entry1 = ttk.Entry(mainframe, width=20, textvariable=self.value) + entry1.grid(column=1, row=1, **defaults) + + ttk.Label(mainframe, text="Result:").grid(column=0, row=4, **defaults) + + entry2 = tk.Entry(mainframe, width=20, state=tk.DISABLED, + textvariable=self.result, + disabledbackground="White Smoke", + disabledforeground="Midnight Blue") + entry2.grid(column=1, row=4, **defaults) + ttk.Button(mainframe, text="Calculate", + command=self.calculate).grid(column=3, row=5, **defaults) + + + def calculate(self): + """Perform calculation""" + action = {1: self._inch_calculate, + 2: self._cm_calculate} + try: + val = int(self.value.get()) + except ValueError: + val = self.value.get() + + result = action[self.convert_to_inches.get()](val) + self.result.set(result) + + def _cm_calculate(self, val): + """Calculate cm value from given val in inch""" + try: + return "%.4f" % val/0.3937 + except TypeError: + return "Err" + + def _inch_calculate(self, val): + """Calculate inch value from given val in cm""" + try: + return "%.4f" % val * 0.3937 + except TypeError: + return "Err" + + +def main(): + """Main function""" + conv = CmInchConverter() + conv.run() + + +if __name__ == '__main__': + main() diff --git a/images/debugs.pdf b/images/debugs.pdf new file mode 100644 index 0000000..037291a Binary files /dev/null and b/images/debugs.pdf differ diff --git a/images/title.pdf b/images/title.pdf new file mode 100644 index 0000000..7b06701 Binary files /dev/null and b/images/title.pdf differ