├── .gitignore ├── LICENSE ├── README.md ├── apps └── todo-cli │ ├── cli0.py │ ├── cli1.py │ └── data.txt ├── media ├── TIMELINE.jpg ├── break.PNG ├── continue.PNG ├── exception.PNG ├── file_methods1.PNG ├── file_methods2.PNG ├── imports.PNG ├── loops.PNG ├── modes.PNG ├── mro.PNG ├── mro1.PNG ├── multilevel.PNG ├── multiple.PNG ├── scopes.PNG └── subpackages.PNG ├── notebooks ├── 1_funamentals_of_python.ipynb ├── 2_controlflow_loops_functions.ipynb ├── 3_exceptions_filehandling.ipynb ├── 4_more_on_functions.ipynb ├── 5_map_reduce_filter_lambda_scoping.ipynb ├── 6_imports_module_packages.ipynb ├── 7_decorators_generators_iterators.ipynb ├── 8_packaging_vnenv.ipynb └── 9_object_oriented_programming.ipynb └── notes /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | 6 | # C extensions 7 | *.so 8 | 9 | # Distribution / packaging 10 | .Python 11 | build/ 12 | develop-eggs/ 13 | dist/ 14 | downloads/ 15 | eggs/ 16 | .eggs/ 17 | lib/ 18 | lib64/ 19 | parts/ 20 | sdist/ 21 | var/ 22 | wheels/ 23 | pip-wheel-metadata/ 24 | share/python-wheels/ 25 | *.egg-info/ 26 | .installed.cfg 27 | *.egg 28 | MANIFEST 29 | 30 | # PyInstaller 31 | # Usually these files are written by a python script from a template 32 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 33 | *.manifest 34 | *.spec 35 | 36 | # Installer logs 37 | pip-log.txt 38 | pip-delete-this-directory.txt 39 | 40 | # Unit test / coverage reports 41 | htmlcov/ 42 | .tox/ 43 | .nox/ 44 | .coverage 45 | .coverage.* 46 | .cache 47 | nosetests.xml 48 | coverage.xml 49 | *.cover 50 | *.py,cover 51 | .hypothesis/ 52 | .pytest_cache/ 53 | 54 | # Translations 55 | *.mo 56 | *.pot 57 | 58 | # Django stuff: 59 | *.log 60 | local_settings.py 61 | db.sqlite3 62 | db.sqlite3-journal 63 | 64 | # Flask stuff: 65 | instance/ 66 | .webassets-cache 67 | 68 | # Scrapy stuff: 69 | .scrapy 70 | 71 | # Sphinx documentation 72 | docs/_build/ 73 | 74 | # PyBuilder 75 | target/ 76 | 77 | # Jupyter Notebook 78 | .ipynb_checkpoints 79 | 80 | # IPython 81 | profile_default/ 82 | ipython_config.py 83 | 84 | # pyenv 85 | .python-version 86 | 87 | # pipenv 88 | # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. 89 | # However, in case of collaboration, if having platform-specific dependencies or dependencies 90 | # having no cross-platform support, pipenv may install dependencies that don't work, or not 91 | # install all needed dependencies. 92 | #Pipfile.lock 93 | 94 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow 95 | __pypackages__/ 96 | 97 | # Celery stuff 98 | celerybeat-schedule 99 | celerybeat.pid 100 | 101 | # SageMath parsed files 102 | *.sage.py 103 | 104 | # Environments 105 | .env 106 | .venv 107 | env/ 108 | venv/ 109 | ENV/ 110 | env.bak/ 111 | venv.bak/ 112 | 113 | # Spyder project settings 114 | .spyderproject 115 | .spyproject 116 | 117 | # Rope project settings 118 | .ropeproject 119 | 120 | # mkdocs documentation 121 | /site 122 | 123 | # mypy 124 | .mypy_cache/ 125 | .dmypy.json 126 | dmypy.json 127 | 128 | # Pyre type checker 129 | .pyre/ 130 | 131 | # VSCODE 132 | .vscode/ 133 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Apache License 2 | Version 2.0, January 2004 3 | http://www.apache.org/licenses/ 4 | 5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 6 | 7 | 1. Definitions. 8 | 9 | "License" shall mean the terms and conditions for use, reproduction, 10 | and distribution as defined by Sections 1 through 9 of this document. 11 | 12 | "Licensor" shall mean the copyright owner or entity authorized by 13 | the copyright owner that is granting the License. 14 | 15 | "Legal Entity" shall mean the union of the acting entity and all 16 | other entities that control, are controlled by, or are under common 17 | control with that entity. For the purposes of this definition, 18 | "control" means (i) the power, direct or indirect, to cause the 19 | direction or management of such entity, whether by contract or 20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 21 | outstanding shares, or (iii) beneficial ownership of such entity. 22 | 23 | "You" (or "Your") shall mean an individual or Legal Entity 24 | exercising permissions granted by this License. 25 | 26 | "Source" form shall mean the preferred form for making modifications, 27 | including but not limited to software source code, documentation 28 | source, and configuration files. 29 | 30 | "Object" form shall mean any form resulting from mechanical 31 | transformation or translation of a Source form, including but 32 | not limited to compiled object code, generated documentation, 33 | and conversions to other media types. 34 | 35 | "Work" shall mean the work of authorship, whether in Source or 36 | Object form, made available under the License, as indicated by a 37 | copyright notice that is included in or attached to the work 38 | (an example is provided in the Appendix below). 39 | 40 | "Derivative Works" shall mean any work, whether in Source or Object 41 | form, that is based on (or derived from) the Work and for which the 42 | editorial revisions, annotations, elaborations, or other modifications 43 | represent, as a whole, an original work of authorship. For the purposes 44 | of this License, Derivative Works shall not include works that remain 45 | separable from, or merely link (or bind by name) to the interfaces of, 46 | the Work and Derivative Works thereof. 47 | 48 | "Contribution" shall mean any work of authorship, including 49 | the original version of the Work and any modifications or additions 50 | to that Work or Derivative Works thereof, that is intentionally 51 | submitted to Licensor for inclusion in the Work by the copyright owner 52 | or by an individual or Legal Entity authorized to submit on behalf of 53 | the copyright owner. For the purposes of this definition, "submitted" 54 | means any form of electronic, verbal, or written communication sent 55 | to the Licensor or its representatives, including but not limited to 56 | communication on electronic mailing lists, source code control systems, 57 | and issue tracking systems that are managed by, or on behalf of, the 58 | Licensor for the purpose of discussing and improving the Work, but 59 | excluding communication that is conspicuously marked or otherwise 60 | designated in writing by the copyright owner as "Not a Contribution." 61 | 62 | "Contributor" shall mean Licensor and any individual or Legal Entity 63 | on behalf of whom a Contribution has been received by Licensor and 64 | subsequently incorporated within the Work. 65 | 66 | 2. Grant of Copyright License. Subject to the terms and conditions of 67 | this License, each Contributor hereby grants to You a perpetual, 68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 69 | copyright license to reproduce, prepare Derivative Works of, 70 | publicly display, publicly perform, sublicense, and distribute the 71 | Work and such Derivative Works in Source or Object form. 72 | 73 | 3. Grant of Patent License. Subject to the terms and conditions of 74 | this License, each Contributor hereby grants to You a perpetual, 75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 76 | (except as stated in this section) patent license to make, have made, 77 | use, offer to sell, sell, import, and otherwise transfer the Work, 78 | where such license applies only to those patent claims licensable 79 | by such Contributor that are necessarily infringed by their 80 | Contribution(s) alone or by combination of their Contribution(s) 81 | with the Work to which such Contribution(s) was submitted. If You 82 | institute patent litigation against any entity (including a 83 | cross-claim or counterclaim in a lawsuit) alleging that the Work 84 | or a Contribution incorporated within the Work constitutes direct 85 | or contributory patent infringement, then any patent licenses 86 | granted to You under this License for that Work shall terminate 87 | as of the date such litigation is filed. 88 | 89 | 4. Redistribution. You may reproduce and distribute copies of the 90 | Work or Derivative Works thereof in any medium, with or without 91 | modifications, and in Source or Object form, provided that You 92 | meet the following conditions: 93 | 94 | (a) You must give any other recipients of the Work or 95 | Derivative Works a copy of this License; and 96 | 97 | (b) You must cause any modified files to carry prominent notices 98 | stating that You changed the files; and 99 | 100 | (c) You must retain, in the Source form of any Derivative Works 101 | that You distribute, all copyright, patent, trademark, and 102 | attribution notices from the Source form of the Work, 103 | excluding those notices that do not pertain to any part of 104 | the Derivative Works; and 105 | 106 | (d) If the Work includes a "NOTICE" text file as part of its 107 | distribution, then any Derivative Works that You distribute must 108 | include a readable copy of the attribution notices contained 109 | within such NOTICE file, excluding those notices that do not 110 | pertain to any part of the Derivative Works, in at least one 111 | of the following places: within a NOTICE text file distributed 112 | as part of the Derivative Works; within the Source form or 113 | documentation, if provided along with the Derivative Works; or, 114 | within a display generated by the Derivative Works, if and 115 | wherever such third-party notices normally appear. The contents 116 | of the NOTICE file are for informational purposes only and 117 | do not modify the License. You may add Your own attribution 118 | notices within Derivative Works that You distribute, alongside 119 | or as an addendum to the NOTICE text from the Work, provided 120 | that such additional attribution notices cannot be construed 121 | as modifying the License. 122 | 123 | You may add Your own copyright statement to Your modifications and 124 | may provide additional or different license terms and conditions 125 | for use, reproduction, or distribution of Your modifications, or 126 | for any such Derivative Works as a whole, provided Your use, 127 | reproduction, and distribution of the Work otherwise complies with 128 | the conditions stated in this License. 129 | 130 | 5. Submission of Contributions. Unless You explicitly state otherwise, 131 | any Contribution intentionally submitted for inclusion in the Work 132 | by You to the Licensor shall be under the terms and conditions of 133 | this License, without any additional terms or conditions. 134 | Notwithstanding the above, nothing herein shall supersede or modify 135 | the terms of any separate license agreement you may have executed 136 | with Licensor regarding such Contributions. 137 | 138 | 6. Trademarks. This License does not grant permission to use the trade 139 | names, trademarks, service marks, or product names of the Licensor, 140 | except as required for reasonable and customary use in describing the 141 | origin of the Work and reproducing the content of the NOTICE file. 142 | 143 | 7. Disclaimer of Warranty. Unless required by applicable law or 144 | agreed to in writing, Licensor provides the Work (and each 145 | Contributor provides its Contributions) on an "AS IS" BASIS, 146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 147 | implied, including, without limitation, any warranties or conditions 148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 149 | PARTICULAR PURPOSE. You are solely responsible for determining the 150 | appropriateness of using or redistributing the Work and assume any 151 | risks associated with Your exercise of permissions under this License. 152 | 153 | 8. Limitation of Liability. In no event and under no legal theory, 154 | whether in tort (including negligence), contract, or otherwise, 155 | unless required by applicable law (such as deliberate and grossly 156 | negligent acts) or agreed to in writing, shall any Contributor be 157 | liable to You for damages, including any direct, indirect, special, 158 | incidental, or consequential damages of any character arising as a 159 | result of this License or out of the use or inability to use the 160 | Work (including but not limited to damages for loss of goodwill, 161 | work stoppage, computer failure or malfunction, or any and all 162 | other commercial damages or losses), even if such Contributor 163 | has been advised of the possibility of such damages. 164 | 165 | 9. Accepting Warranty or Additional Liability. While redistributing 166 | the Work or Derivative Works thereof, You may choose to offer, 167 | and charge a fee for, acceptance of support, warranty, indemnity, 168 | or other liability obligations and/or rights consistent with this 169 | License. However, in accepting such obligations, You may act only 170 | on Your own behalf and on Your sole responsibility, not on behalf 171 | of any other Contributor, and only if You agree to indemnify, 172 | defend, and hold each Contributor harmless for any liability 173 | incurred by, or claims asserted against, such Contributor by reason 174 | of your accepting any such warranty or additional liability. 175 | 176 | END OF TERMS AND CONDITIONS 177 | 178 | APPENDIX: How to apply the Apache License to your work. 179 | 180 | To apply the Apache License to your work, attach the following 181 | boilerplate notice, with the fields enclosed by brackets "[]" 182 | replaced with your own identifying information. (Don't include 183 | the brackets!) The text should be enclosed in the appropriate 184 | comment syntax for the file format. We also recommend that a 185 | file or class name and description of purpose be included on the 186 | same "printed page" as the copyright notice for easier 187 | identification within third-party archives. 188 | 189 | Copyright [yyyy] [name of copyright owner] 190 | 191 | Licensed under the Apache License, Version 2.0 (the "License"); 192 | you may not use this file except in compliance with the License. 193 | You may obtain a copy of the License at 194 | 195 | http://www.apache.org/licenses/LICENSE-2.0 196 | 197 | Unless required by applicable law or agreed to in writing, software 198 | distributed under the License is distributed on an "AS IS" BASIS, 199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 200 | See the License for the specific language governing permissions and 201 | limitations under the License. 202 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Python for DevOps 2 | This training content is primarily developed for engineers who are working in DevOps & Cloud domain and want to learn Python. That may help them to either automate lot of the stuff they work on in their respective domain or give them new opportunies in their career. 3 | 4 | ### Pre-requisites 5 | Basic understanding of any programming language 6 | 7 | ### What we'll cover in this training 8 | 9 | - [Session 1](https://github.com/inovizz/python-for-devops/blob/master/notebooks/1_funamentals_of_python.ipynb) 10 | - Data types 11 | - Data Structures (Collection Objects) 12 | - Namespaces 13 | - Mutable and Immutable objects 14 | 15 | - [Session 2](https://github.com/inovizz/python-for-devops/blob/master/notebooks/2_controlflow_loops_functions.ipynb) 16 | - If/else (Control Flow) 17 | - Loops 18 | - Functions 19 | 20 | - [Session 3](https://github.com/inovizz/python-for-devops/blob/master/notebooks/3_exceptions_filehandling.ipynb) & [CLI App - Demo](https://github.com/inovizz/python-for-devops/tree/master/apps/todo-cli) 21 | - Input/Output 22 | - File Handling 23 | - Developing a CLI App in Python 24 | 25 | - [Session 4](https://github.com/inovizz/python-for-devops/blob/master/notebooks/3_exceptions_filehandling.ipynb) 26 | - Import 27 | - Exception handling 28 | - File handling 29 | 30 | - [Session 5](https://github.com/inovizz/python-for-devops/blob/master/notebooks/4_more_on_functions.ipynb) 31 | - More on functions 32 | - Arbitrary Arguments 33 | - Keyword Arguments 34 | - Positional Arguments 35 | 36 | - [Session 6](https://github.com/inovizz/python-for-devops/blob/master/notebooks/5_map_reduce_filter_lambda_scoping.ipynb) 37 | - Lambda Functions 38 | - Map, Filter & Redume 39 | - Comprehensions 40 | - Scope - (Global, Local & Nonlocal) 41 | 42 | - [Session 7](https://github.com/inovizz/python-for-devops/blob/master/notebooks/6_imports_module_packages.ipynb) 43 | - Understanding \_\_name_\_ builtin 44 | - Use of \_\_name_\_ == "\_\_main_\_" 45 | - Modules & Packages 46 | - How import works 47 | 48 | - [Session 8](https://github.com/inovizz/python-for-devops/blob/master/notebooks/7_decorators_generators_iterators.ipynb) 49 | - Decorators 50 | - Iterators 51 | - Generators 52 | - PDB module 53 | 54 | - [Session 9](https://github.com/inovizz/python-for-devops/blob/master/notebooks/8_packaging_vnenv.ipynb) 55 | - PyPi & pip 56 | - How pip install works? 57 | - What is virtualenv 58 | - Creating your own Package 59 | 60 | - [Session 10](https://github.com/inovizz/python-for-devops/blob/master/notebooks/9_object_oriented_programming.ipynb) 61 | - Class 62 | - Objects 63 | - Instance & Class Attributes 64 | - Self keyword 65 | - \_\_init\_\_ & \_\_new\_\_ methods 66 | - classmethod, staticmethod & instance methods 67 | - Practical usage of @classmethod 68 | - Inheritance 69 | - Super Method 70 | - What super method can do for you? 71 | - Encapsulation 72 | - Multiple Inheritance 73 | - MRO 74 | - Polymorphism 75 | 76 | - Session 10 (TBA) 77 | - Working with command line (sys module) 78 | - Working with os module 79 | - Working with datetime and time module 80 | - Working with re module 81 | - Http.server (small intro) 82 | - Urllib (small intro) 83 | - XML parser (small intro) 84 | 85 | - Session 11 (TBA) 86 | - REST API 87 | - Introduction to flask (APIs) 88 | - Introduction to Requests library 89 | - Intro to Authentication & Authorization 90 | 91 | - Sesseion 12 (TBA) 92 | - Unit testing 93 | - Logging 94 | - Mocking 95 | - Fixtures 96 | 97 | - Session 13 (TBA) 98 | - Ftplib (for FTP) 99 | - Subprocess module 100 | - Paramiko 101 | 102 | - Session 14 (TBA) 103 | - Cron jobs using Python 104 | - Health check and alerts using Python 105 | - Intro to CLI frameworks (cement) 106 | 107 | - Session 15 (TBA) 108 | - Intro to multithreading 109 | 110 | - Session 16 (TBA) 111 | - Multiprocessing library 112 | 113 | ---------------------------------------------------- 114 | #### Credits & Reference: 115 | - https://realpython.com/ 116 | - https://gist.github.com/kenjyco/69eeb503125035f21a9d 117 | - https://github.com/jerry-git/learn-python3 118 | - https://www.programiz.com/python-programming 119 | -------------------------------------------------------------------------------- /apps/todo-cli/cli0.py: -------------------------------------------------------------------------------- 1 | import os 2 | 3 | FILE_LOC = "data.txt" 4 | 5 | # color related code for better view on terminal 6 | colors = { 7 | 'DANGER': '\033[91m', 8 | 'WARNING': '\033[33m', 9 | 'MILD': '\033[94m', 10 | 'OK': '\033[92m', 11 | 'RESET': '\033[0m', 12 | 'BLUE': '\033[94m', 13 | 'CYAN': '\033[96m', 14 | } 15 | 16 | format = {0: 5, 1:25, 2:10, 3:25, 4:5} 17 | 18 | # function to get the colored text 19 | def color(text, text_color): 20 | if text_color in colors: 21 | return ''.join([colors[text_color], text, colors['RESET']]) 22 | return text 23 | 24 | # the help text 25 | print("""Usage of the ToDo App CLI\nWe support following commands as of now\n""") 26 | print('Command List') 27 | print("\t" + color("Add item", 'CYAN') + " " + color('--add', 'OK')) 28 | # print("\t" + color("Add due date", 'CYAN') + " " + color('--due', 'OK')) 29 | print("\t" + color("Remove an Item", 'CYAN') + " " + color('--remove', 'OK')) 30 | print("\t" + color("Mark item done", 'CYAN') + " " + color('--done', 'OK')) 31 | print("\t" + color("Mark item not done", 'CYAN') + " " + color('--undone', 'OK')) 32 | print("\t" + color("View items", 'CYAN') + " " + color('--view', 'OK')) 33 | 34 | cmd = input("Enter the command ") 35 | 36 | if cmd: 37 | # Add the item 38 | if cmd == "--add": 39 | print(color("Add your task in following format", 'BLUE')) 40 | print(color("'Title', 'Due Date', 'Description'\n", 'CYAN')) 41 | data = input() 42 | data = data.split(",") 43 | data = ", ".join(data) 44 | if data: 45 | with open(FILE_LOC, 'r+') as f: 46 | last_line = f.readlines()[-1] 47 | if last_line: 48 | try: 49 | count = int(last_line.split(",")[0])+1 50 | except ValueError: 51 | count = 1 52 | f.write(str(count)+", "+data+", [ ]""\n") 53 | print(color("Item successfully added!", 'CYAN')) 54 | # remove the item 55 | elif cmd == "--remove": 56 | print("\n"+color("Remove your task by providing the id of the task", 'BLUE')) 57 | try: 58 | id = int(input("Enter the id of the task you want to delete ")) 59 | except ValueError: 60 | raise("Please enter the correct id value") 61 | with open(FILE_LOC, 'r') as f: 62 | lines = f.readlines() 63 | with open(FILE_LOC, 'w+') as f: 64 | count = 0 65 | for line in lines: 66 | if count == 0: 67 | f.write(line) 68 | count += 1 69 | continue 70 | no = int(line.split(", ")[0]) 71 | if no != id: 72 | f.write(line) 73 | count += 1 74 | print(color("Item successfully removed!", 'CYAN')) 75 | # mark the item as done 76 | elif cmd == "--done": 77 | print("\n"+color("Mark your task as done by providing the id of the task", 'BLUE')) 78 | try: 79 | id = int(input("Enter the id of the task you want to mark as done ")) 80 | except ValueError: 81 | raise("Please enter the correct id value") 82 | with open(FILE_LOC, 'r') as f: 83 | lines = f.readlines() 84 | with open(FILE_LOC, 'w+') as f: 85 | count = 0 86 | for line in lines: 87 | if count == 0: 88 | f.write(line) 89 | count += 1 90 | continue 91 | no = int(line.split(", ")[0]) 92 | if no == id: 93 | line_text = line.split(", ") 94 | line_text[-1] = "[x]\n" 95 | line = ", ".join(line_text) 96 | f.write(line) 97 | else: 98 | f.write(line) 99 | count += 1 100 | print(color("Item successfully updated!", 'CYAN')) 101 | # mark the item as undone 102 | elif cmd == "--undone": 103 | print("\n"+color("Mark your task as undone by providing the id of the task", 'BLUE')) 104 | try: 105 | id = int(input("Enter the id of the task you want to mark as undone ")) 106 | except ValueError: 107 | raise("Please enter the correct id value") 108 | with open(FILE_LOC, 'r') as f: 109 | lines = f.readlines() 110 | with open(FILE_LOC, 'w+') as f: 111 | count = 0 112 | for line in lines: 113 | if count == 0: 114 | f.write(line) 115 | count += 1 116 | continue 117 | no = int(line.split(", ")[0]) 118 | if no == id: 119 | line_text = line.split(", ") 120 | line_text[-1] = "[ ]\n" 121 | line = ", ".join(line_text) 122 | f.write(line) 123 | else: 124 | f.write(line) 125 | count += 1 126 | print(color("Item successfully updated!", 'CYAN')) 127 | # list all the todo items 128 | elif cmd == "--view": 129 | with open(FILE_LOC, 'r') as f: 130 | lines = f.readlines() 131 | count = 0 132 | for line in lines: 133 | data = [] 134 | line = line.split(", ") 135 | for i in range(len(line)): 136 | data.append(line[i].strip().ljust(format[i])) 137 | if count == 0: 138 | print(color(" ".join(data), 'OK')) 139 | else: 140 | print(color(" ".join(data), 'RESET')) 141 | count += 1 142 | else: 143 | print("Command not found, please run the script again and check the help") 144 | -------------------------------------------------------------------------------- /apps/todo-cli/cli1.py: -------------------------------------------------------------------------------- 1 | import argparse 2 | 3 | parser = argparse.ArgumentParser(description="My todo-cli app") 4 | 5 | parser.add_argument('--add', help='Add a new item to my ToDo List', type=str, nargs='+') 6 | parser.add_argument('--remove', help='Remove item from my ToDo List', type=int) 7 | parser.add_argument('--done', help='Mark the item as done from my ToDo List', type=int) 8 | parser.add_argument('--undone', help='Mark item as not done from my ToDo List', type=int) 9 | parser.add_argument('--view', help='View the ToDo list or view a specific item from ToDo List', type=int, nargs='*') 10 | parser.add_argument('--description', help='Add description to a ToDo item', nargs='*') 11 | parser.add_argument('--due', help='Add due date for an ToDo item', nargs='*') 12 | 13 | 14 | if __name__ == "__main__": 15 | args = parser.parse_args() 16 | if args.add: 17 | print("added the ToDo Item") -------------------------------------------------------------------------------- /apps/todo-cli/data.txt: -------------------------------------------------------------------------------- 1 | ID, Title, DueDate, Description, Status 2 | -------------------------------------------------------------------------------- /media/TIMELINE.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/TIMELINE.jpg -------------------------------------------------------------------------------- /media/break.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/break.PNG -------------------------------------------------------------------------------- /media/continue.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/continue.PNG -------------------------------------------------------------------------------- /media/exception.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/exception.PNG -------------------------------------------------------------------------------- /media/file_methods1.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/file_methods1.PNG -------------------------------------------------------------------------------- /media/file_methods2.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/file_methods2.PNG -------------------------------------------------------------------------------- /media/imports.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/imports.PNG -------------------------------------------------------------------------------- /media/loops.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/loops.PNG -------------------------------------------------------------------------------- /media/modes.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/modes.PNG -------------------------------------------------------------------------------- /media/mro.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/mro.PNG -------------------------------------------------------------------------------- /media/mro1.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/mro1.PNG -------------------------------------------------------------------------------- /media/multilevel.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/multilevel.PNG -------------------------------------------------------------------------------- /media/multiple.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/multiple.PNG -------------------------------------------------------------------------------- /media/scopes.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/scopes.PNG -------------------------------------------------------------------------------- /media/subpackages.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/inovizz/python-for-devops/526c87b5c457ee5c32cb5c6bd22e0e19940a9db1/media/subpackages.PNG -------------------------------------------------------------------------------- /notebooks/2_controlflow_loops_functions.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# Session 2 - Control Flow, Loops and Functions" 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": { 13 | "slideshow": { 14 | "slide_type": "slide" 15 | } 16 | }, 17 | "source": [ 18 | "## If Statements" 19 | ] 20 | }, 21 | { 22 | "cell_type": "markdown", 23 | "metadata": { 24 | "slideshow": { 25 | "slide_type": "slide" 26 | } 27 | }, 28 | "source": [ 29 | "What is an *if* statement?\n", 30 | "===\n", 31 | "An *if* statement tests for a condition, and then responds to that condition. If the condition is true, then whatever action is listed next gets carried out. You can test for multiple conditions at the same time, and respond appropriately to each condition." 32 | ] 33 | }, 34 | { 35 | "cell_type": "markdown", 36 | "metadata": { 37 | "slideshow": { 38 | "slide_type": "slide" 39 | } 40 | }, 41 | "source": [ 42 | "The if-elif...else chain\n", 43 | "===\n", 44 | "You can test whatever series of conditions you want to, and you can test your conditions in any combination you want." 45 | ] 46 | }, 47 | { 48 | "cell_type": "markdown", 49 | "metadata": { 50 | "slideshow": { 51 | "slide_type": "subslide" 52 | } 53 | }, 54 | "source": [ 55 | "Simple if statements\n", 56 | "---\n", 57 | "The simplest test has a single **if** statement, and a single statement to execute if the condition is **True**." 58 | ] 59 | }, 60 | { 61 | "cell_type": "code", 62 | "execution_count": 54, 63 | "metadata": { 64 | "slideshow": { 65 | "slide_type": "fragment" 66 | } 67 | }, 68 | "outputs": [ 69 | { 70 | "name": "stdout", 71 | "output_type": "stream", 72 | "text": [ 73 | "Wow, we have a lot of robbers here!\n" 74 | ] 75 | } 76 | ], 77 | "source": [ 78 | "robbers = ['berlin', 'moscow', 'rio', 'tokyo']\n", 79 | "\n", 80 | "if len(robbers) > 3:\n", 81 | " print(\"Wow, we have a lot of robbers here!\")" 82 | ] 83 | }, 84 | { 85 | "cell_type": "code", 86 | "execution_count": 55, 87 | "metadata": { 88 | "slideshow": { 89 | "slide_type": "fragment" 90 | } 91 | }, 92 | "outputs": [], 93 | "source": [ 94 | "robbers = ['berlin', 'moscow']\n", 95 | "\n", 96 | "if len(robbers) > 3:\n", 97 | " print(\"Wow, we have a lot of robbers here!\")" 98 | ] 99 | }, 100 | { 101 | "cell_type": "markdown", 102 | "metadata": { 103 | "slideshow": { 104 | "slide_type": "fragment" 105 | } 106 | }, 107 | "source": [ 108 | "Notice that there are no errors. The condition `len(robbers) > 3` evaluates to False, and the program moves on to any lines after the **if** block." 109 | ] 110 | }, 111 | { 112 | "cell_type": "markdown", 113 | "metadata": { 114 | "slideshow": { 115 | "slide_type": "subslide" 116 | } 117 | }, 118 | "source": [ 119 | "if-else statements\n", 120 | "---\n", 121 | "Many times you will want to respond in two possible ways to a test. If the test evaluates to **True**, you will want to do one thing. If the test evaluates to **False**, you will want to do something else. The **if-else** structure lets you do that easily. Here's what it looks like:" 122 | ] 123 | }, 124 | { 125 | "cell_type": "code", 126 | "execution_count": 57, 127 | "metadata": { 128 | "slideshow": { 129 | "slide_type": "fragment" 130 | } 131 | }, 132 | "outputs": [ 133 | { 134 | "name": "stdout", 135 | "output_type": "stream", 136 | "text": [ 137 | "Okay, this is a reasonable number of robbers.\n" 138 | ] 139 | } 140 | ], 141 | "source": [ 142 | "robbers = ['berlin', 'moscow', 'rio', 'tokyo']\n", 143 | "\n", 144 | "if len(robbers) > 3:\n", 145 | " print(\"Wow, we have a lot of robbers here!\")\n", 146 | "else:\n", 147 | " print(\"Okay, this is a reasonable number of robbers.\")" 148 | ] 149 | }, 150 | { 151 | "cell_type": "markdown", 152 | "metadata": { 153 | "slideshow": { 154 | "slide_type": "subslide" 155 | } 156 | }, 157 | "source": [ 158 | "Our results have not changed in this case, because if the test evaluates to **True** only the statements under the **if** statement are executed. The statements under **else** area only executed if the test fails:" 159 | ] 160 | }, 161 | { 162 | "cell_type": "code", 163 | "execution_count": 59, 164 | "metadata": { 165 | "slideshow": { 166 | "slide_type": "fragment" 167 | } 168 | }, 169 | "outputs": [ 170 | { 171 | "name": "stdout", 172 | "output_type": "stream", 173 | "text": [ 174 | "Okay, this is a reasonable number of robbers.\n" 175 | ] 176 | } 177 | ], 178 | "source": [ 179 | "robbers = ['berlin', 'moscow']\n", 180 | "\n", 181 | "if len(robbers) > 3:\n", 182 | " print(\"Wow, we have a lot of robbers here!\")\n", 183 | "else:\n", 184 | " print(\"Okay, this is a reasonable number of robbers.\")" 185 | ] 186 | }, 187 | { 188 | "cell_type": "markdown", 189 | "metadata": { 190 | "slideshow": { 191 | "slide_type": "fragment" 192 | } 193 | }, 194 | "source": [ 195 | "The test evaluated to **False**, so only the statement under `else` is run." 196 | ] 197 | }, 198 | { 199 | "cell_type": "markdown", 200 | "metadata": { 201 | "slideshow": { 202 | "slide_type": "subslide" 203 | } 204 | }, 205 | "source": [ 206 | "if-elif...else chains\n", 207 | "---\n", 208 | "Many times, you will want to test a series of conditions, rather than just an either-or situation. You can do this with a series of if-elif-else statements\n", 209 | "\n", 210 | "There is no limit to how many conditions you can test. You always need one if statement to start the chain, and you can never have more than one else statement. But you can have as many elif statements as you want." 211 | ] 212 | }, 213 | { 214 | "cell_type": "code", 215 | "execution_count": 60, 216 | "metadata": { 217 | "slideshow": { 218 | "slide_type": "fragment" 219 | } 220 | }, 221 | "outputs": [ 222 | { 223 | "name": "stdout", 224 | "output_type": "stream", 225 | "text": [ 226 | "Holy shit!, the whole money heist team is here!\n" 227 | ] 228 | } 229 | ], 230 | "source": [ 231 | "robbers = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi', 'professor']\n", 232 | "\n", 233 | "if len(robbers) >= 5:\n", 234 | " print(\"Holy shit!, the whole money heist team is here!\")\n", 235 | "elif len(robbers) >= 3:\n", 236 | " print(\"Wow, we have a lot of robbers here!\")\n", 237 | "else:\n", 238 | " print(\"Okay, this is a reasonable number of robbers.\")" 239 | ] 240 | }, 241 | { 242 | "cell_type": "markdown", 243 | "metadata": { 244 | "slideshow": { 245 | "slide_type": "subslide" 246 | } 247 | }, 248 | "source": [ 249 | "It is important to note that in situations like this, only the first test is evaluated. In an if-elif-else chain, once a test passes the rest of the conditions are ignored." 250 | ] 251 | }, 252 | { 253 | "cell_type": "code", 254 | "execution_count": 61, 255 | "metadata": { 256 | "slideshow": { 257 | "slide_type": "fragment" 258 | } 259 | }, 260 | "outputs": [ 261 | { 262 | "name": "stdout", 263 | "output_type": "stream", 264 | "text": [ 265 | "Wow, we have a lot of robbers here!\n" 266 | ] 267 | } 268 | ], 269 | "source": [ 270 | "robbers = ['berlin', 'moscow', 'rio', 'denver']\n", 271 | "\n", 272 | "if len(robbers) >= 5:\n", 273 | " print(\"Holy shit!, the whole money heist team is here!\")\n", 274 | "elif len(robbers) >= 3:\n", 275 | " print(\"Wow, we have a lot of robbers here!\")\n", 276 | "else:\n", 277 | " print(\"Okay, this is a reasonable number of robbers.\")" 278 | ] 279 | }, 280 | { 281 | "cell_type": "markdown", 282 | "metadata": { 283 | "slideshow": { 284 | "slide_type": "subslide" 285 | } 286 | }, 287 | "source": [ 288 | "The first test failed, so Python evaluated the second test. That test passed, so the statement corresponding to `len(robbers) >= 3` is executed." 289 | ] 290 | }, 291 | { 292 | "cell_type": "code", 293 | "execution_count": 62, 294 | "metadata": { 295 | "slideshow": { 296 | "slide_type": "fragment" 297 | } 298 | }, 299 | "outputs": [ 300 | { 301 | "name": "stdout", 302 | "output_type": "stream", 303 | "text": [ 304 | "Okay, this is a reasonable number of robbers.\n" 305 | ] 306 | } 307 | ], 308 | "source": [ 309 | "robbers = ['berlin', 'moscow']\n", 310 | "\n", 311 | "if len(robbers) >= 5:\n", 312 | " print(\"Holy shit!, the whole money heist team is here!\")\n", 313 | "elif len(robbers) >= 3:\n", 314 | " print(\"Wow, we have a lot of robbers here!\")\n", 315 | "else:\n", 316 | " print(\"Okay, this is a reasonable number of robbers.\")" 317 | ] 318 | }, 319 | { 320 | "cell_type": "markdown", 321 | "metadata": { 322 | "slideshow": { 323 | "slide_type": "subslide" 324 | } 325 | }, 326 | "source": [ 327 | "In this situation, the first two tests fail, so the statement in the else clause is executed. Note that this statement would be executed even if there are no robbers at all:" 328 | ] 329 | }, 330 | { 331 | "cell_type": "code", 332 | "execution_count": 63, 333 | "metadata": { 334 | "slideshow": { 335 | "slide_type": "fragment" 336 | } 337 | }, 338 | "outputs": [ 339 | { 340 | "name": "stdout", 341 | "output_type": "stream", 342 | "text": [ 343 | "Okay, this is a reasonable number of robbers.\n" 344 | ] 345 | } 346 | ], 347 | "source": [ 348 | "robbers = []\n", 349 | "\n", 350 | "if len(robbers) >= 5:\n", 351 | " print(\"Holy shit!, the whole money heist team is here!\")\n", 352 | "elif len(robbers) >= 3:\n", 353 | " print(\"Wow, we have a lot of robbers here!\")\n", 354 | "else:\n", 355 | " print(\"Okay, this is a reasonable number of robbers.\")" 356 | ] 357 | }, 358 | { 359 | "cell_type": "markdown", 360 | "metadata": { 361 | "slideshow": { 362 | "slide_type": "subslide" 363 | } 364 | }, 365 | "source": [ 366 | "Note that you don't have to take any action at all when you start a series of if statements. You could simply do nothing in the situation that there are no robbers by replacing the `else` clause with another `elif` clause:" 367 | ] 368 | }, 369 | { 370 | "cell_type": "code", 371 | "execution_count": 64, 372 | "metadata": {}, 373 | "outputs": [ 374 | { 375 | "data": { 376 | "text/plain": [ 377 | "False" 378 | ] 379 | }, 380 | "execution_count": 64, 381 | "metadata": {}, 382 | "output_type": "execute_result" 383 | } 384 | ], 385 | "source": [ 386 | "robbers = ['berlin', 'moscow', 'rio', 'denver']\n", 387 | "\n", 388 | "'professor' in robbers" 389 | ] 390 | }, 391 | { 392 | "cell_type": "code", 393 | "execution_count": 67, 394 | "metadata": { 395 | "slideshow": { 396 | "slide_type": "subslide" 397 | } 398 | }, 399 | "outputs": [ 400 | { 401 | "name": "stdout", 402 | "output_type": "stream", 403 | "text": [ 404 | "Hello, berlin! and Moscow\n" 405 | ] 406 | } 407 | ], 408 | "source": [ 409 | "robbers = ['berlin', 'moscow']\n", 410 | "\n", 411 | "if ('berlin' in robbers) or ('moscow' in robbers):\n", 412 | " print(\"Hello, berlin! and Moscow\")\n", 413 | "elif 'moscow' in robbers:\n", 414 | " print(\"Hello, moscow!\")\n", 415 | "elif 'rio' in robbers:\n", 416 | " print(\"Hello, rio!\")\n", 417 | "elif 'denver' in robbers:\n", 418 | " print(\"Hello, denver!\")" 419 | ] 420 | }, 421 | { 422 | "cell_type": "code", 423 | "execution_count": null, 424 | "metadata": { 425 | "slideshow": { 426 | "slide_type": "fragment" 427 | } 428 | }, 429 | "outputs": [], 430 | "source": [ 431 | "robbers = ['berlin', 'moscow']\n", 432 | "\n", 433 | "if 'berlin' in robbers:\n", 434 | " print(\"Hello, berlin!\")\n", 435 | "elif 'moscow' in robbers:\n", 436 | " print(\"Hello, moscow!\")\n", 437 | "elif 'rio' in robbers:\n", 438 | " print(\"Hello, rio!\")\n", 439 | "elif 'denver' in robbers:\n", 440 | " print(\"Hello, denver!\")" 441 | ] 442 | }, 443 | { 444 | "cell_type": "markdown", 445 | "metadata": { 446 | "slideshow": { 447 | "slide_type": "subslide" 448 | } 449 | }, 450 | "source": [ 451 | "Of course, this could be written much more cleanly using lists and for loops. See if you can follow this code." 452 | ] 453 | }, 454 | { 455 | "cell_type": "code", 456 | "execution_count": null, 457 | "metadata": { 458 | "slideshow": { 459 | "slide_type": "fragment" 460 | } 461 | }, 462 | "outputs": [], 463 | "source": [ 464 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi']\n", 465 | "robbers_present = ['berlin', 'moscow']\n", 466 | "\n", 467 | "# Go through all the robbers that are present, and greet the robbers we know.\n", 468 | "for robber in robbers_present:\n", 469 | " if robber in robbers_we_know:\n", 470 | " print(\"Hello, %s!\" % robber.title())" 471 | ] 472 | }, 473 | { 474 | "cell_type": "markdown", 475 | "metadata": { 476 | "slideshow": { 477 | "slide_type": "fragment" 478 | } 479 | }, 480 | "source": [ 481 | "This is the kind of code you should be aiming to write. It is fine to come up with code that is less efficient at first. When you notice yourself writing the same kind of code repeatedly in one program, look to see if you can use a loop or a function to make your code more efficient." 482 | ] 483 | }, 484 | { 485 | "cell_type": "markdown", 486 | "metadata": { 487 | "slideshow": { 488 | "slide_type": "slide" 489 | } 490 | }, 491 | "source": [ 492 | "True and False values\n", 493 | "===\n", 494 | "Every value can be evaluated as True or False. The general rule is that any non-zero or non-empty value will evaluate to True. If you are ever unsure, you can open a Python terminal and write two lines to find out if the value you are considering is True or False." 495 | ] 496 | }, 497 | { 498 | "cell_type": "markdown", 499 | "metadata": { 500 | "slideshow": { 501 | "slide_type": "fragment" 502 | } 503 | }, 504 | "source": [ 505 | "Take a look at the following examples, keep them in mind, and test any value you are curious about." 506 | ] 507 | }, 508 | { 509 | "cell_type": "code", 510 | "execution_count": 70, 511 | "metadata": { 512 | "slideshow": { 513 | "slide_type": "fragment" 514 | } 515 | }, 516 | "outputs": [ 517 | { 518 | "name": "stdout", 519 | "output_type": "stream", 520 | "text": [ 521 | "This evaluates to False.\n" 522 | ] 523 | } 524 | ], 525 | "source": [ 526 | "if 0:\n", 527 | " print(\"This evaluates to True.\")\n", 528 | "else:\n", 529 | " print(\"This evaluates to False.\")" 530 | ] 531 | }, 532 | { 533 | "cell_type": "code", 534 | "execution_count": 69, 535 | "metadata": {}, 536 | "outputs": [ 537 | { 538 | "data": { 539 | "text/plain": [ 540 | "False" 541 | ] 542 | }, 543 | "execution_count": 69, 544 | "metadata": {}, 545 | "output_type": "execute_result" 546 | } 547 | ], 548 | "source": [] 549 | }, 550 | { 551 | "cell_type": "code", 552 | "execution_count": 71, 553 | "metadata": { 554 | "slideshow": { 555 | "slide_type": "fragment" 556 | } 557 | }, 558 | "outputs": [ 559 | { 560 | "name": "stdout", 561 | "output_type": "stream", 562 | "text": [ 563 | "This evaluates to True.\n" 564 | ] 565 | } 566 | ], 567 | "source": [ 568 | "if 1:\n", 569 | " print(\"This evaluates to True.\")\n", 570 | "else:\n", 571 | " print(\"This evaluates to False.\")" 572 | ] 573 | }, 574 | { 575 | "cell_type": "code", 576 | "execution_count": 72, 577 | "metadata": { 578 | "slideshow": { 579 | "slide_type": "subslide" 580 | } 581 | }, 582 | "outputs": [ 583 | { 584 | "name": "stdout", 585 | "output_type": "stream", 586 | "text": [ 587 | "This evaluates to True.\n" 588 | ] 589 | } 590 | ], 591 | "source": [ 592 | "# Arbitrary non-zero numbers evaluate to True.\n", 593 | "if 1253756:\n", 594 | " print(\"This evaluates to True.\")\n", 595 | "else:\n", 596 | " print(\"This evaluates to False.\")" 597 | ] 598 | }, 599 | { 600 | "cell_type": "code", 601 | "execution_count": 73, 602 | "metadata": { 603 | "slideshow": { 604 | "slide_type": "fragment" 605 | } 606 | }, 607 | "outputs": [ 608 | { 609 | "name": "stdout", 610 | "output_type": "stream", 611 | "text": [ 612 | "This evaluates to True.\n" 613 | ] 614 | } 615 | ], 616 | "source": [ 617 | "# Negative numbers are not zero, so they evaluate to True.\n", 618 | "if -1:\n", 619 | " print(\"This evaluates to True.\")\n", 620 | "else:\n", 621 | " print(\"This evaluates to False.\")" 622 | ] 623 | }, 624 | { 625 | "cell_type": "code", 626 | "execution_count": 75, 627 | "metadata": { 628 | "slideshow": { 629 | "slide_type": "subslide" 630 | } 631 | }, 632 | "outputs": [ 633 | { 634 | "name": "stdout", 635 | "output_type": "stream", 636 | "text": [ 637 | "This evaluates to False.\n" 638 | ] 639 | } 640 | ], 641 | "source": [ 642 | "# An empty string evaluates to False.\n", 643 | "if '':\n", 644 | " print(\"This evaluates to True.\")\n", 645 | "else:\n", 646 | " print(\"This evaluates to False.\")" 647 | ] 648 | }, 649 | { 650 | "cell_type": "code", 651 | "execution_count": 76, 652 | "metadata": { 653 | "slideshow": { 654 | "slide_type": "fragment" 655 | } 656 | }, 657 | "outputs": [ 658 | { 659 | "name": "stdout", 660 | "output_type": "stream", 661 | "text": [ 662 | "This evaluates to True.\n" 663 | ] 664 | } 665 | ], 666 | "source": [ 667 | "# Any other string, including a space, evaluates to True.\n", 668 | "if ' ':\n", 669 | " print(\"This evaluates to True.\")\n", 670 | "else:\n", 671 | " print(\"This evaluates to False.\")" 672 | ] 673 | }, 674 | { 675 | "cell_type": "code", 676 | "execution_count": 77, 677 | "metadata": { 678 | "slideshow": { 679 | "slide_type": "subslide" 680 | } 681 | }, 682 | "outputs": [ 683 | { 684 | "name": "stdout", 685 | "output_type": "stream", 686 | "text": [ 687 | "This evaluates to True.\n" 688 | ] 689 | } 690 | ], 691 | "source": [ 692 | "# Any other string, including a space, evaluates to True.\n", 693 | "if 'hello':\n", 694 | " print(\"This evaluates to True.\")\n", 695 | "else:\n", 696 | " print(\"This evaluates to False.\")" 697 | ] 698 | }, 699 | { 700 | "cell_type": "code", 701 | "execution_count": 78, 702 | "metadata": { 703 | "slideshow": { 704 | "slide_type": "fragment" 705 | } 706 | }, 707 | "outputs": [ 708 | { 709 | "name": "stdout", 710 | "output_type": "stream", 711 | "text": [ 712 | "This evaluates to False.\n" 713 | ] 714 | } 715 | ], 716 | "source": [ 717 | "# None is a special object in Python. It evaluates to False.\n", 718 | "if None:\n", 719 | " print(\"This evaluates to True.\")\n", 720 | "else:\n", 721 | " print(\"This evaluates to False.\")" 722 | ] 723 | }, 724 | { 725 | "attachments": {}, 726 | "cell_type": "markdown", 727 | "metadata": {}, 728 | "source": [ 729 | "Loops\n", 730 | "---\n", 731 | "\n", 732 | "#### For Loops\n", 733 | "\n", 734 | "\n", 735 | "" 736 | ] 737 | }, 738 | { 739 | "cell_type": "code", 740 | "execution_count": 84, 741 | "metadata": {}, 742 | "outputs": [ 743 | { 744 | "name": "stdout", 745 | "output_type": "stream", 746 | "text": [ 747 | "berlin\n", 748 | "moscow\n", 749 | "rio\n", 750 | "denver\n", 751 | "tokyo\n", 752 | "naomi\n" 753 | ] 754 | } 755 | ], 756 | "source": [ 757 | "# for loop syntax using in operator\n", 758 | "\n", 759 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi']\n", 760 | "\n", 761 | "for robber in robbers_we_know:\n", 762 | " print(robber)\n", 763 | " " 764 | ] 765 | }, 766 | { 767 | "cell_type": "code", 768 | "execution_count": null, 769 | "metadata": {}, 770 | "outputs": [], 771 | "source": [ 772 | "# TODO \n", 773 | "Timeit" 774 | ] 775 | }, 776 | { 777 | "cell_type": "markdown", 778 | "metadata": {}, 779 | "source": [ 780 | "range() function\n", 781 | "---\n" 782 | ] 783 | }, 784 | { 785 | "cell_type": "code", 786 | "execution_count": 85, 787 | "metadata": {}, 788 | "outputs": [ 789 | { 790 | "name": "stdout", 791 | "output_type": "stream", 792 | "text": [ 793 | "berlin\n", 794 | "moscow\n", 795 | "rio\n", 796 | "denver\n", 797 | "tokyo\n", 798 | "naomi\n" 799 | ] 800 | } 801 | ], 802 | "source": [ 803 | "for i in range(len(robbers_we_know)):\n", 804 | " print(robbers_we_know[i])" 805 | ] 806 | }, 807 | { 808 | "cell_type": "code", 809 | "execution_count": 81, 810 | "metadata": {}, 811 | "outputs": [ 812 | { 813 | "name": "stdout", 814 | "output_type": "stream", 815 | "text": [ 816 | "range(0, 10)\n", 817 | "[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]\n", 818 | "[2, 3, 4, 5, 6, 7]\n", 819 | "[2, 5, 8, 11, 14, 17]\n" 820 | ] 821 | } 822 | ], 823 | "source": [ 824 | "# using range function\n", 825 | "\n", 826 | "print(range(10))\n", 827 | "\n", 828 | "print(list(range(10)))\n", 829 | "\n", 830 | "print(list(range(2, 8)))\n", 831 | "\n", 832 | "print(list(range(2, 20, 3)))" 833 | ] 834 | }, 835 | { 836 | "cell_type": "markdown", 837 | "metadata": {}, 838 | "source": [ 839 | "### How to use for else" 840 | ] 841 | }, 842 | { 843 | "cell_type": "code", 844 | "execution_count": 88, 845 | "metadata": {}, 846 | "outputs": [ 847 | { 848 | "name": "stdout", 849 | "output_type": "stream", 850 | "text": [ 851 | "do something\n", 852 | "do something\n", 853 | "do something\n", 854 | "do something\n", 855 | "do something\n", 856 | "do something\n", 857 | "Professor is arrested\n" 858 | ] 859 | } 860 | ], 861 | "source": [ 862 | "# using for else syntax\n", 863 | "\n", 864 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi']\n", 865 | "\n", 866 | "for robber in robbers_we_know:\n", 867 | " if robber == 'professor':\n", 868 | " break\n", 869 | " else:\n", 870 | " print('do something')\n", 871 | "else:\n", 872 | " print(\"Professor is arrested\")" 873 | ] 874 | }, 875 | { 876 | "cell_type": "code", 877 | "execution_count": 91, 878 | "metadata": {}, 879 | "outputs": [ 880 | { 881 | "name": "stdout", 882 | "output_type": "stream", 883 | "text": [ 884 | "moscow\n", 885 | "rio\n", 886 | "denver\n", 887 | "tokyo\n", 888 | "naomi\n", 889 | "loop completed, do something now\n" 890 | ] 891 | } 892 | ], 893 | "source": [ 894 | "# another example and pass statement\n", 895 | "\n", 896 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi']\n", 897 | "\n", 898 | "for robber in robbers_we_know:\n", 899 | " if robber == \"berlin\":\n", 900 | " pass\n", 901 | " else:\n", 902 | " print(robber)\n", 903 | "else:\n", 904 | " print(\"loop completed, do something now\")\n" 905 | ] 906 | }, 907 | { 908 | "attachments": {}, 909 | "cell_type": "markdown", 910 | "metadata": {}, 911 | "source": [ 912 | "### Use of break statement\n", 913 | "\n", 914 | "" 915 | ] 916 | }, 917 | { 918 | "cell_type": "code", 919 | "execution_count": 92, 920 | "metadata": {}, 921 | "outputs": [ 922 | { 923 | "name": "stdout", 924 | "output_type": "stream", 925 | "text": [ 926 | "Robber catched with name berlin\n", 927 | "Robber catched with name moscow\n", 928 | "Robber catched with name rio\n", 929 | "3 robbers catched, that's enough for today\n" 930 | ] 931 | } 932 | ], 933 | "source": [ 934 | "# break statement\n", 935 | "count = 0\n", 936 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi']\n", 937 | "\n", 938 | "for robber in robbers_we_know:\n", 939 | " print(\"Robber catched with name\", robber)\n", 940 | " count += 1\n", 941 | " if count == 3:\n", 942 | " print(\"3 robbers catched, that's enough for today\")\n", 943 | " break\n", 944 | " " 945 | ] 946 | }, 947 | { 948 | "attachments": {}, 949 | "cell_type": "markdown", 950 | "metadata": {}, 951 | "source": [ 952 | "### Use of Continue statement\n", 953 | "\n", 954 | "" 955 | ] 956 | }, 957 | { 958 | "cell_type": "code", 959 | "execution_count": 98, 960 | "metadata": {}, 961 | "outputs": [ 962 | { 963 | "name": "stdout", 964 | "output_type": "stream", 965 | "text": [ 966 | "Professor we got you!\n" 967 | ] 968 | } 969 | ], 970 | "source": [ 971 | "# continue statement\n", 972 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi', 'professor']\n", 973 | "\n", 974 | "for robber in robbers_we_know:\n", 975 | " if robber != 'professor':\n", 976 | " pass\n", 977 | " print('Professor we got you!')\n", 978 | " " 979 | ] 980 | }, 981 | { 982 | "cell_type": "markdown", 983 | "metadata": {}, 984 | "source": [ 985 | "### While Loops" 986 | ] 987 | }, 988 | { 989 | "cell_type": "markdown", 990 | "metadata": {}, 991 | "source": [ 992 | "A while loop tests an initial condition. If that condition is true, the loop starts executing. Every time the loop finishes, the condition is reevaluated. As long as the condition remains true, the loop keeps executing. As soon as the condition becomes false, the loop stops executing." 993 | ] 994 | }, 995 | { 996 | "cell_type": "code", 997 | "execution_count": null, 998 | "metadata": {}, 999 | "outputs": [], 1000 | "source": [ 1001 | "# Set an initial condition.\n", 1002 | "game_active = True\n", 1003 | "\n", 1004 | "# Set up the while loop.\n", 1005 | "while game_active:\n", 1006 | " # Run the game.\n", 1007 | " # At some point, the game ends and game_active will be set to False.\n", 1008 | " # When that happens, the loop will stop executing.\n", 1009 | " \n", 1010 | "# Do anything else you want done after the loop runs." 1011 | ] 1012 | }, 1013 | { 1014 | "cell_type": "markdown", 1015 | "metadata": {}, 1016 | "source": [ 1017 | "- Every while loop needs an initial condition that starts out true.\n", 1018 | "- The while statement includes a condition to test.\n", 1019 | "- All of the code in the loop will run as long as the condition remains true.\n", 1020 | "- As soon as something in the loop changes the condition such that the test no longer passes, the loop stops executing.\n", 1021 | "- Any code that is defined after the loop will run at this point." 1022 | ] 1023 | }, 1024 | { 1025 | "cell_type": "code", 1026 | "execution_count": 1, 1027 | "metadata": {}, 1028 | "outputs": [ 1029 | { 1030 | "name": "stdout", 1031 | "output_type": "stream", 1032 | "text": [ 1033 | "berlin\n", 1034 | "moscow\n", 1035 | "rio\n", 1036 | "denver\n", 1037 | "tokyo\n", 1038 | "naomi\n", 1039 | "loop execution finished, do something if you want!\n" 1040 | ] 1041 | } 1042 | ], 1043 | "source": [ 1044 | "robbers_we_know = ['berlin', 'moscow', 'rio', 'denver', 'tokyo', 'naomi']\n", 1045 | "\n", 1046 | "i = 0\n", 1047 | "\n", 1048 | "while (iWhat are functions?\n", 1188 | "===\n", 1189 | "Functions are a set of actions that we group together, and give a name to. You have already used a number of functions from the core Python language, such as *string.title()* and *list.sort()*. We can define our own functions, which allows us to \"teach\" Python new behavior." 1190 | ] 1191 | }, 1192 | { 1193 | "cell_type": "markdown", 1194 | "metadata": {}, 1195 | "source": [ 1196 | "General Syntax\n", 1197 | "---\n", 1198 | "A general function looks something like this:" 1199 | ] 1200 | }, 1201 | { 1202 | "cell_type": "code", 1203 | "execution_count": 13, 1204 | "metadata": {}, 1205 | "outputs": [ 1206 | { 1207 | "ename": "IndentationError", 1208 | "evalue": "expected an indented block (, line 7)", 1209 | "output_type": "error", 1210 | "traceback": [ 1211 | "\u001b[1;36m File \u001b[1;32m\"\"\u001b[1;36m, line \u001b[1;32m7\u001b[0m\n\u001b[1;33m function_name(value_1, value_2)\u001b[0m\n\u001b[1;37m ^\u001b[0m\n\u001b[1;31mIndentationError\u001b[0m\u001b[1;31m:\u001b[0m expected an indented block\n" 1212 | ] 1213 | } 1214 | ], 1215 | "source": [ 1216 | "# Let's define a function.\n", 1217 | "def function_name(argument_1, argument_2):\n", 1218 | " # Do whatever we want this function to do,\n", 1219 | " # using argument_1 and argument_2\n", 1220 | " \n", 1221 | "# Use function_name to call the function.\n", 1222 | "function_name(value_1, value_2)" 1223 | ] 1224 | }, 1225 | { 1226 | "cell_type": "code", 1227 | "execution_count": 14, 1228 | "metadata": {}, 1229 | "outputs": [ 1230 | { 1231 | "name": "stdout", 1232 | "output_type": "stream", 1233 | "text": [ 1234 | "Our robbers are currently in alphabetical order.\n", 1235 | "Berlin\n", 1236 | "Denvor\n", 1237 | "Monica\n", 1238 | "Rio\n", 1239 | "\n", 1240 | "Our robbers are now in reverse alphabetical order.\n", 1241 | "Rio\n", 1242 | "Monica\n", 1243 | "Denvor\n", 1244 | "Berlin\n" 1245 | ] 1246 | } 1247 | ], 1248 | "source": [ 1249 | "# something without a function\n", 1250 | "\n", 1251 | "robbers = ['denvor', 'monica', 'rio', 'berlin']\n", 1252 | "\n", 1253 | "# Put students in alphabetical order.\n", 1254 | "robbers.sort()\n", 1255 | "\n", 1256 | "# Display the list in its current order.\n", 1257 | "print(\"Our robbers are currently in alphabetical order.\")\n", 1258 | "for robber in robbers:\n", 1259 | " print(robber.title())\n", 1260 | "\n", 1261 | "# Put robbers in reverse alphabetical order.\n", 1262 | "robbers.sort(reverse=True)\n", 1263 | "\n", 1264 | "# Display the list in its current order.\n", 1265 | "print(\"\\nOur robbers are now in reverse alphabetical order.\")\n", 1266 | "for robber in robbers:\n", 1267 | " print(robber.title())" 1268 | ] 1269 | }, 1270 | { 1271 | "cell_type": "code", 1272 | "execution_count": 20, 1273 | "metadata": {}, 1274 | "outputs": [ 1275 | { 1276 | "name": "stdout", 1277 | "output_type": "stream", 1278 | "text": [ 1279 | "Our robbers are currently in alphabetical order.\n", 1280 | "Berlin\n", 1281 | "Denvor\n", 1282 | "Monica\n", 1283 | "Rio\n", 1284 | "\n", 1285 | "Our robbers are currently in reverse alphabetical order.\n", 1286 | "Rio\n", 1287 | "Monica\n", 1288 | "Denvor\n", 1289 | "Berlin\n" 1290 | ] 1291 | } 1292 | ], 1293 | "source": [ 1294 | "# now with a function\n", 1295 | "\n", 1296 | "def print_robbers(robbers, message):\n", 1297 | " print(message)\n", 1298 | " for robber in robbers:\n", 1299 | " print(robber.title())\n", 1300 | " \n", 1301 | "\n", 1302 | "robbers = ['denvor', 'monica', 'rio', 'berlin']\n", 1303 | "\n", 1304 | "# Put robbers in alphabetical order.\n", 1305 | "message = \"Our robbers are currently in alphabetical order.\"\n", 1306 | "robbers.sort()\n", 1307 | "print_robbers(robbers, message)\n", 1308 | "\n", 1309 | "# Put robbers in reverse alphabetical order.\n", 1310 | "message = \"\\nOur robbers are currently in reverse alphabetical order.\"\n", 1311 | "robbers.sort(reverse=True)\n", 1312 | "print_robbers(robbers, message)\n", 1313 | "\n" 1314 | ] 1315 | }, 1316 | { 1317 | "cell_type": "markdown", 1318 | "metadata": {}, 1319 | "source": [ 1320 | "Returning a Value\n", 1321 | "---\n", 1322 | "Each function you create can return a value. This can be in addition to the primary work the function does, or it can be the function's main job. The following function takes in a number, and returns the corresponding word for that number:" 1323 | ] 1324 | }, 1325 | { 1326 | "cell_type": "code", 1327 | "execution_count": 22, 1328 | "metadata": {}, 1329 | "outputs": [ 1330 | { 1331 | "name": "stdout", 1332 | "output_type": "stream", 1333 | "text": [ 1334 | "1 ('one', 'one', 'one')\n", 1335 | "2 two\n", 1336 | "3 three\n", 1337 | "4 This is an unknown number\n", 1338 | "5 This is an unknown number\n", 1339 | "6 This is an unknown number\n", 1340 | "7 This is an unknown number\n", 1341 | "8 This is an unknown number\n", 1342 | "9 This is an unknown number\n" 1343 | ] 1344 | } 1345 | ], 1346 | "source": [ 1347 | "def get_number_word(number):\n", 1348 | " # Takes in a numerical value, and returns\n", 1349 | " # the word corresponding to that number.\n", 1350 | " if number == 1:\n", 1351 | " return 'one', 'one', 'one'\n", 1352 | " elif number == 2:\n", 1353 | " return 'two'\n", 1354 | " elif number == 3:\n", 1355 | " return 'three'\n", 1356 | " else:\n", 1357 | " return \"This is an unknown number\"\n", 1358 | " \n", 1359 | "# Let's try out our function.\n", 1360 | "for current_number in range(1,10):\n", 1361 | " number_word = get_number_word(current_number)\n", 1362 | " print(current_number, number_word)" 1363 | ] 1364 | }, 1365 | { 1366 | "cell_type": "code", 1367 | "execution_count": null, 1368 | "metadata": {}, 1369 | "outputs": [], 1370 | "source": [] 1371 | } 1372 | ], 1373 | "metadata": { 1374 | "kernelspec": { 1375 | "display_name": "Python 3", 1376 | "language": "python", 1377 | "name": "python3" 1378 | }, 1379 | "language_info": { 1380 | "codemirror_mode": { 1381 | "name": "ipython", 1382 | "version": 3 1383 | }, 1384 | "file_extension": ".py", 1385 | "mimetype": "text/x-python", 1386 | "name": "python", 1387 | "nbconvert_exporter": "python", 1388 | "pygments_lexer": "ipython3", 1389 | "version": "3.7.5" 1390 | } 1391 | }, 1392 | "nbformat": 4, 1393 | "nbformat_minor": 1 1394 | } 1395 | -------------------------------------------------------------------------------- /notebooks/3_exceptions_filehandling.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# File Handling" 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "Opening and Closing a File in Python\n", 15 | "When you want to work with a file, the first thing to do is to open it. This is done by invoking the open() built-in function. open() has a single required argument that is the path to the file. open() has a single return, the file object:" 16 | ] 17 | }, 18 | { 19 | "cell_type": "code", 20 | "execution_count": 71, 21 | "metadata": {}, 22 | "outputs": [], 23 | "source": [ 24 | "file = open('Session1-variable_data_types.ipynb', encoding=\"utf-8\")\n", 25 | "\n", 26 | "# ToDO - Read about encoding works and which encoding should be used while playing around with string and file" 27 | ] 28 | }, 29 | { 30 | "cell_type": "code", 31 | "execution_count": 68, 32 | "metadata": {}, 33 | "outputs": [ 34 | { 35 | "name": "stdout", 36 | "output_type": "stream", 37 | "text": [ 38 | " Volume in drive C is EPINHYDW1086\n", 39 | " Volume Serial Number is 4247-02EF\n", 40 | "\n", 41 | " Directory of C:\\cygwin64\\home\\Sanchit_Balchandani\\Workspace\\python-ws\\python-for-devops\\notebooks\n", 42 | "\n", 43 | "06/02/2020 03:46 PM .\n", 44 | "06/02/2020 03:46 PM ..\n", 45 | "06/02/2020 02:59 PM .ipynb_checkpoints\n", 46 | "05/29/2020 02:53 PM 46,971 Session1-variable_data_types.ipynb\n", 47 | "05/29/2020 03:39 PM 293,225 Session2-ControlFlow, Loops & functions.ipynb\n", 48 | "06/02/2020 02:47 PM 232,945 Session3 - Exceptions & File Handling.ipynb\n", 49 | "06/02/2020 03:46 PM 22,939 Session3 - More on Functions.ipynb\n", 50 | " 4 File(s) 596,080 bytes\n", 51 | " 3 Dir(s) 78,167,195,648 bytes free\n" 52 | ] 53 | } 54 | ], 55 | "source": [ 56 | "ls" 57 | ] 58 | }, 59 | { 60 | "cell_type": "code", 61 | "execution_count": 72, 62 | "metadata": { 63 | "scrolled": true 64 | }, 65 | "outputs": [ 66 | { 67 | "data": { 68 | "text/plain": [ 69 | "<_io.TextIOWrapper name='Session1-variable_data_types.ipynb' mode='r' encoding='utf-8'>" 70 | ] 71 | }, 72 | "execution_count": 72, 73 | "metadata": {}, 74 | "output_type": "execute_result" 75 | } 76 | ], 77 | "source": [ 78 | "file" 79 | ] 80 | }, 81 | { 82 | "cell_type": "code", 83 | "execution_count": 77, 84 | "metadata": {}, 85 | "outputs": [], 86 | "source": [ 87 | "open?" 88 | ] 89 | }, 90 | { 91 | "cell_type": "code", 92 | "execution_count": 74, 93 | "metadata": {}, 94 | "outputs": [], 95 | "source": [ 96 | "# close the file\n", 97 | "file.close()" 98 | ] 99 | }, 100 | { 101 | "cell_type": "code", 102 | "execution_count": 75, 103 | "metadata": {}, 104 | "outputs": [ 105 | { 106 | "ename": "ValueError", 107 | "evalue": "I/O operation on closed file.", 108 | "output_type": "error", 109 | "traceback": [ 110 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 111 | "\u001b[1;31mValueError\u001b[0m Traceback (most recent call last)", 112 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[1;32m----> 1\u001b[1;33m \u001b[0mfile\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mread\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 113 | "\u001b[1;31mValueError\u001b[0m: I/O operation on closed file." 114 | ] 115 | } 116 | ], 117 | "source": [ 118 | "file.read()" 119 | ] 120 | }, 121 | { 122 | "cell_type": "code", 123 | "execution_count": 90, 124 | "metadata": {}, 125 | "outputs": [ 126 | { 127 | "name": "stdout", 128 | "output_type": "stream", 129 | "text": [ 130 | "7\n" 131 | ] 132 | } 133 | ], 134 | "source": [ 135 | "# another way of opening file and making sure it gets closed\n", 136 | "with open('Session1-variable_data_types.ipynb', 'r+', encoding='utf-8') as f:\n", 137 | " print(f.write(\"kljdlkj\"))\n" 138 | ] 139 | }, 140 | { 141 | "cell_type": "code", 142 | "execution_count": 89, 143 | "metadata": {}, 144 | "outputs": [ 145 | { 146 | "ename": "TypeError", 147 | "evalue": "a bytes-like object is required, not 'str'", 148 | "output_type": "error", 149 | "traceback": [ 150 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 151 | "\u001b[1;31mTypeError\u001b[0m Traceback (most recent call last)", 152 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 1\u001b[0m \u001b[1;32mwith\u001b[0m \u001b[0mopen\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"file.txt\"\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'ab'\u001b[0m\u001b[1;33m)\u001b[0m \u001b[1;32mas\u001b[0m \u001b[0mf\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 2\u001b[1;33m \u001b[0mf\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mwrite\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Hey there!\\n\"\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 153 | "\u001b[1;31mTypeError\u001b[0m: a bytes-like object is required, not 'str'" 154 | ] 155 | } 156 | ], 157 | "source": [ 158 | "with open(\"file.txt\", 'ab') as f:\n", 159 | " f.write(\"Hey there!\\n\")" 160 | ] 161 | }, 162 | { 163 | "attachments": {}, 164 | "cell_type": "markdown", 165 | "metadata": {}, 166 | "source": [ 167 | "### modes\n", 168 | "\n", 169 | "We can specify the mode while opening a file. In mode, we specify whether we want to read r, write w or append a to the file. We can also specify if we want to open the file in text mode or binary mode.\n", 170 | "\n", 171 | "The default is reading in text mode. In this mode, we get strings when reading from the file.\n", 172 | "\n", 173 | "On the other hand, binary mode returns bytes and this is the mode to be used when dealing with non-text files like images or executable files.\n", 174 | "\n", 175 | "" 176 | ] 177 | }, 178 | { 179 | "cell_type": "code", 180 | "execution_count": null, 181 | "metadata": {}, 182 | "outputs": [], 183 | "source": [ 184 | "# TODO explore the other file modes like t, X" 185 | ] 186 | }, 187 | { 188 | "cell_type": "markdown", 189 | "metadata": {}, 190 | "source": [ 191 | "There are three different categories of file objects:\n", 192 | "\n", 193 | "- Text files\n", 194 | "- Buffered binary files\n", 195 | "- Raw binary files\n", 196 | "\n", 197 | "Each of these file types are defined in the io module. Here’s a quick rundown of how everything lines up." 198 | ] 199 | }, 200 | { 201 | "cell_type": "code", 202 | "execution_count": 44, 203 | "metadata": {}, 204 | "outputs": [], 205 | "source": [ 206 | "f = open('../apps/todo-cli/data.txt')\n", 207 | "\n", 208 | "f1 = open('../apps/todo-cli/data.txt', 'r')\n", 209 | "\n", 210 | "f2 = open('../apps/todo-cli/data.txt', 'w')" 211 | ] 212 | }, 213 | { 214 | "cell_type": "code", 215 | "execution_count": 46, 216 | "metadata": {}, 217 | "outputs": [ 218 | { 219 | "name": "stdout", 220 | "output_type": "stream", 221 | "text": [ 222 | "<_io.TextIOWrapper name='../apps/todo-cli/data.txt' mode='r' encoding='cp1252'>\n", 223 | "<_io.TextIOWrapper name='../apps/todo-cli/data.txt' mode='r' encoding='cp1252'>\n", 224 | "<_io.TextIOWrapper name='../apps/todo-cli/data.txt' mode='w' encoding='cp1252'>\n" 225 | ] 226 | } 227 | ], 228 | "source": [ 229 | "print(f, f1, f2, sep=\"\\n\")" 230 | ] 231 | }, 232 | { 233 | "cell_type": "code", 234 | "execution_count": 48, 235 | "metadata": {}, 236 | "outputs": [], 237 | "source": [ 238 | "f1 = open('../apps/todo-cli/data.txt', 'rb')\n", 239 | "\n", 240 | "f2 = open('../apps/todo-cli/data.txt', 'wb')" 241 | ] 242 | }, 243 | { 244 | "cell_type": "code", 245 | "execution_count": 49, 246 | "metadata": { 247 | "scrolled": true 248 | }, 249 | "outputs": [ 250 | { 251 | "name": "stdout", 252 | "output_type": "stream", 253 | "text": [ 254 | "<_io.BufferedReader name='../apps/todo-cli/data.txt'>\n", 255 | "<_io.BufferedWriter name='../apps/todo-cli/data.txt'>\n" 256 | ] 257 | } 258 | ], 259 | "source": [ 260 | "print(f1, f2, sep=\"\\n\")" 261 | ] 262 | }, 263 | { 264 | "cell_type": "markdown", 265 | "metadata": {}, 266 | "source": [ 267 | "Reading Files in Python\n", 268 | "\n", 269 | "\n", 270 | "To read a file in Python, we must open the file in reading r mode.\n", 271 | "\n", 272 | "There are various methods available for this purpose. We can use the read(size) method to read in the size number of data. If the size parameter is not specified, it reads and returns up to the end of the file.\n", 273 | "\n", 274 | "We can read the text.txt file we wrote in the above section in the following way:" 275 | ] 276 | }, 277 | { 278 | "cell_type": "code", 279 | "execution_count": 94, 280 | "metadata": { 281 | "scrolled": true 282 | }, 283 | "outputs": [ 284 | { 285 | "name": "stdout", 286 | "output_type": "stream", 287 | "text": [ 288 | "ID, \n", 289 | "Titl\n", 290 | "e, DueDate, Description, Status\n", 291 | "1, Session-4 prep, today, Demostrate CLI app again, [ ]\n", 292 | "\n" 293 | ] 294 | } 295 | ], 296 | "source": [ 297 | "f = open(\"../apps/todo-cli/data.txt\", 'r',encoding = 'utf-8')\n", 298 | "print(f.read(4)) # read the first 4 data\n", 299 | "\n", 300 | "print(f.read(4)) # read the next 4 data\n", 301 | "\n", 302 | "\n", 303 | "print(f.read()) # read in the rest till end of file\n" 304 | ] 305 | }, 306 | { 307 | "cell_type": "code", 308 | "execution_count": 73, 309 | "metadata": {}, 310 | "outputs": [ 311 | { 312 | "name": "stdout", 313 | "output_type": "stream", 314 | "text": [ 315 | "ID, Title, DueDate, Description, Status\n", 316 | "Something SomethingSomething Something\n" 317 | ] 318 | } 319 | ], 320 | "source": [ 321 | "f = open(\"../apps/todo-cli/data.txt\", 'r+',encoding = 'utf-8')\n", 322 | "data = f.read()\n", 323 | "print(data)\n", 324 | "f.write(\"Something Something\")\n", 325 | "f.close()\n", 326 | "\n", 327 | "# f = open(\"../apps/todo-cli/data.txt\", 'r+',encoding = 'utf-8')\n", 328 | "# data = f.read()\n", 329 | "# print(data)" 330 | ] 331 | }, 332 | { 333 | "cell_type": "code", 334 | "execution_count": null, 335 | "metadata": {}, 336 | "outputs": [], 337 | "source": [] 338 | }, 339 | { 340 | "cell_type": "code", 341 | "execution_count": 95, 342 | "metadata": { 343 | "scrolled": true 344 | }, 345 | "outputs": [ 346 | { 347 | "name": "stdout", 348 | "output_type": "stream", 349 | "text": [ 350 | "100\n" 351 | ] 352 | }, 353 | { 354 | "data": { 355 | "text/plain": [ 356 | "0" 357 | ] 358 | }, 359 | "execution_count": 95, 360 | "metadata": {}, 361 | "output_type": "execute_result" 362 | } 363 | ], 364 | "source": [ 365 | "# We can change our current file cursor (position) using the seek() method. \n", 366 | "# Similarly, the tell() method returns our current position (in number of bytes).\n", 367 | "print(f.tell())\n", 368 | "f.seek(0)" 369 | ] 370 | }, 371 | { 372 | "cell_type": "code", 373 | "execution_count": 96, 374 | "metadata": { 375 | "scrolled": true 376 | }, 377 | "outputs": [ 378 | { 379 | "data": { 380 | "text/plain": [ 381 | "'ID, Title, DueDate, Description, Status\\n1, Session-4 prep, today, Demostrate CLI app again, [ ]\\n'" 382 | ] 383 | }, 384 | "execution_count": 96, 385 | "metadata": {}, 386 | "output_type": "execute_result" 387 | } 388 | ], 389 | "source": [ 390 | "f.read()" 391 | ] 392 | }, 393 | { 394 | "cell_type": "markdown", 395 | "metadata": {}, 396 | "source": [ 397 | "Python File Methods\n", 398 | "There are various methods available with the file object. Some of them have been used in the above examples.\n", 399 | "\n", 400 | "Here is the complete list of methods in text mode with a brief description:" 401 | ] 402 | }, 403 | { 404 | "attachments": {}, 405 | "cell_type": "markdown", 406 | "metadata": {}, 407 | "source": [ 408 | "\n", 409 | "" 410 | ] 411 | }, 412 | { 413 | "cell_type": "markdown", 414 | "metadata": {}, 415 | "source": [ 416 | "# Exceptions" 417 | ] 418 | }, 419 | { 420 | "cell_type": "markdown", 421 | "metadata": {}, 422 | "source": [ 423 | "Exceptions which are events that can modify the *flow* of control through a program. \n", 424 | "\n", 425 | "In Python, exceptions are triggered automatically on errors, and they can be triggered and intercepted by your code.\n", 426 | "\n", 427 | "They are processed by **four** statements we’ll study in this notebook, the first of which has two variations (listed separately here) and the last of which was an optional extension until Python 2.6 and 3.0:\n", 428 | "\n", 429 | "* `try/except`:\n", 430 | " * Catch and recover from exceptions raised by Python, or by you\n", 431 | " \n", 432 | "* `try/finally`:\n", 433 | " * Perform cleanup actions, whether exceptions occur or not.\n", 434 | "\n", 435 | "* `raise`:\n", 436 | " * Trigger an exception manually in your code.\n", 437 | " \n", 438 | "* `assert`:\n", 439 | " * Conditionally trigger an exception in your code.\n", 440 | " " 441 | ] 442 | }, 443 | { 444 | "cell_type": "code", 445 | "execution_count": 2, 446 | "metadata": {}, 447 | "outputs": [ 448 | { 449 | "ename": "ZeroDivisionError", 450 | "evalue": "division by zero", 451 | "output_type": "error", 452 | "traceback": [ 453 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 454 | "\u001b[1;31mZeroDivisionError\u001b[0m Traceback (most recent call last)", 455 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 1\u001b[0m \u001b[1;31m# Exceptions\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 2\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 3\u001b[1;33m \u001b[1;36m1\u001b[0m\u001b[1;33m/\u001b[0m\u001b[1;36m0\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 456 | "\u001b[1;31mZeroDivisionError\u001b[0m: division by zero" 457 | ] 458 | } 459 | ], 460 | "source": [ 461 | "# Exceptions - Example 1\n", 462 | "\n", 463 | "1/0" 464 | ] 465 | }, 466 | { 467 | "cell_type": "code", 468 | "execution_count": 74, 469 | "metadata": {}, 470 | "outputs": [ 471 | { 472 | "ename": "SyntaxError", 473 | "evalue": "EOL while scanning string literal (, line 1)", 474 | "output_type": "error", 475 | "traceback": [ 476 | "\u001b[1;36m File \u001b[1;32m\"\"\u001b[1;36m, line \u001b[1;32m1\u001b[0m\n\u001b[1;33m print(\"jkhfkhk)\u001b[0m\n\u001b[1;37m ^\u001b[0m\n\u001b[1;31mSyntaxError\u001b[0m\u001b[1;31m:\u001b[0m EOL while scanning string literal\n" 477 | ] 478 | } 479 | ], 480 | "source": [ 481 | "print(\"jkhfkhk)" 482 | ] 483 | }, 484 | { 485 | "cell_type": "code", 486 | "execution_count": 75, 487 | "metadata": {}, 488 | "outputs": [ 489 | { 490 | "ename": "TypeError", 491 | "evalue": "can only concatenate str (not \"int\") to str", 492 | "output_type": "error", 493 | "traceback": [ 494 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 495 | "\u001b[1;31mTypeError\u001b[0m Traceback (most recent call last)", 496 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 1\u001b[0m \u001b[1;31m# Exceptions - Example 2\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 2\u001b[1;33m \u001b[1;34m\"sanchit\"\u001b[0m\u001b[1;33m+\u001b[0m\u001b[1;36m5\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 497 | "\u001b[1;31mTypeError\u001b[0m: can only concatenate str (not \"int\") to str" 498 | ] 499 | } 500 | ], 501 | "source": [ 502 | "# Exceptions - Example 2\n", 503 | "\"sanchit\"+Obj" 504 | ] 505 | }, 506 | { 507 | "cell_type": "code", 508 | "execution_count": 76, 509 | "metadata": { 510 | "scrolled": true 511 | }, 512 | "outputs": [ 513 | { 514 | "ename": "KeyError", 515 | "evalue": "5", 516 | "output_type": "error", 517 | "traceback": [ 518 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 519 | "\u001b[1;31mKeyError\u001b[0m Traceback (most recent call last)", 520 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 1\u001b[0m \u001b[1;31m# Exceptions - Example 3\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 2\u001b[0m \u001b[0md\u001b[0m \u001b[1;33m=\u001b[0m \u001b[1;33m{\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m:\u001b[0m \u001b[1;36m2\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m3\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;36m4\u001b[0m\u001b[1;33m}\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 3\u001b[1;33m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0md\u001b[0m\u001b[1;33m[\u001b[0m\u001b[1;36m5\u001b[0m\u001b[1;33m]\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 521 | "\u001b[1;31mKeyError\u001b[0m: 5" 522 | ] 523 | } 524 | ], 525 | "source": [ 526 | "# Exceptions - Example 3\n", 527 | "d = {1: 2, 3:4}\n", 528 | "print(d[5])" 529 | ] 530 | }, 531 | { 532 | "cell_type": "code", 533 | "execution_count": 77, 534 | "metadata": { 535 | "scrolled": false 536 | }, 537 | "outputs": [ 538 | { 539 | "name": "stdout", 540 | "output_type": "stream", 541 | "text": [ 542 | "[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]\n", 543 | "1\n", 544 | "1\n", 545 | "2\n", 546 | "2\n", 547 | "3\n", 548 | "3\n", 549 | "4\n", 550 | "4\n", 551 | "5\n", 552 | "5\n", 553 | "6\n", 554 | "6\n", 555 | "7\n", 556 | "7\n", 557 | "8\n", 558 | "8\n", 559 | "9\n", 560 | "9\n", 561 | "10\n" 562 | ] 563 | }, 564 | { 565 | "ename": "IndexError", 566 | "evalue": "list index out of range", 567 | "output_type": "error", 568 | "traceback": [ 569 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 570 | "\u001b[1;31mIndexError\u001b[0m Traceback (most recent call last)", 571 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 7\u001b[0m \u001b[1;32mfor\u001b[0m \u001b[0mi\u001b[0m \u001b[1;32min\u001b[0m \u001b[0marr\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 8\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mx\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 9\u001b[1;33m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0marr\u001b[0m\u001b[1;33m[\u001b[0m\u001b[0mx\u001b[0m\u001b[1;33m]\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 10\u001b[0m \u001b[0mx\u001b[0m \u001b[1;33m+=\u001b[0m \u001b[1;36m1\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n", 572 | "\u001b[1;31mIndexError\u001b[0m: list index out of range" 573 | ] 574 | } 575 | ], 576 | "source": [ 577 | "# Exceptions - Example 4\n", 578 | "\n", 579 | "arr = list(range(10))\n", 580 | "print(arr)\n", 581 | "\n", 582 | "x = 1\n", 583 | "for i in arr:\n", 584 | " print(x)\n", 585 | " print(arr[x])\n", 586 | " x += 1\n" 587 | ] 588 | }, 589 | { 590 | "attachments": {}, 591 | "cell_type": "markdown", 592 | "metadata": {}, 593 | "source": [ 594 | "#### Raising an Exception\n", 595 | "\n", 596 | "We can use raise to throw an exception if a condition occurs. The statement can be complemented with a custom exception.\n", 597 | "\n", 598 | "" 599 | ] 600 | }, 601 | { 602 | "cell_type": "code", 603 | "execution_count": 78, 604 | "metadata": {}, 605 | "outputs": [ 606 | { 607 | "ename": "Exception", 608 | "evalue": "x should not exceed 5. The value of x was: 10", 609 | "output_type": "error", 610 | "traceback": [ 611 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 612 | "\u001b[1;31mException\u001b[0m Traceback (most recent call last)", 613 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 3\u001b[0m \u001b[0mx\u001b[0m \u001b[1;33m=\u001b[0m \u001b[1;36m10\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 4\u001b[0m \u001b[1;32mif\u001b[0m \u001b[0mx\u001b[0m \u001b[1;33m>\u001b[0m \u001b[1;36m5\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 5\u001b[1;33m \u001b[1;32mraise\u001b[0m \u001b[0mException\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m'x should not exceed 5. The value of x was: {}'\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mformat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mx\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 614 | "\u001b[1;31mException\u001b[0m: x should not exceed 5. The value of x was: 10" 615 | ] 616 | } 617 | ], 618 | "source": [ 619 | "# how to raise exceptions forcefully\n", 620 | "\n", 621 | "x = 10\n", 622 | "if x > 5:\n", 623 | " raise Exception('x should not exceed 5. The value of x was: {}'.format(x))" 624 | ] 625 | }, 626 | { 627 | "cell_type": "code", 628 | "execution_count": 82, 629 | "metadata": {}, 630 | "outputs": [ 631 | { 632 | "ename": "AssertionError", 633 | "evalue": "", 634 | "output_type": "error", 635 | "traceback": [ 636 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 637 | "\u001b[1;31mAssertionError\u001b[0m Traceback (most recent call last)", 638 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 1\u001b[0m \u001b[1;31m# Use of Assert statements\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 2\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 3\u001b[1;33m \u001b[1;32massert\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Sanchit!\"\u001b[0m \u001b[1;32min\u001b[0m \u001b[1;33m[\u001b[0m\u001b[1;34m\"Sanchit\"\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m\"Balchandani\"\u001b[0m\u001b[1;33m]\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 4\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 5\u001b[0m \u001b[1;31m# if \"Sanchit!\" in [\"Sanchit\", \"Balchandani\"]:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n", 639 | "\u001b[1;31mAssertionError\u001b[0m: " 640 | ] 641 | } 642 | ], 643 | "source": [ 644 | "# Use of Assert statements\n", 645 | "\n", 646 | "assert(\"Sanchit!\" in [\"Sanchit\", \"Balchandani\"])\n", 647 | "\n", 648 | "# if \"Sanchit!\" in [\"Sanchit\", \"Balchandani\"]:\n", 649 | "# print(\"Somethhing\")\n", 650 | "# else:\n", 651 | "# print(\"Something else\")" 652 | ] 653 | }, 654 | { 655 | "cell_type": "code", 656 | "execution_count": 79, 657 | "metadata": {}, 658 | "outputs": [ 659 | { 660 | "data": { 661 | "text/plain": [ 662 | "False" 663 | ] 664 | }, 665 | "execution_count": 79, 666 | "metadata": {}, 667 | "output_type": "execute_result" 668 | } 669 | ], 670 | "source": [ 671 | "\"Sanchit!\" in [\"Sanchit\", \"Balchandani\"]" 672 | ] 673 | }, 674 | { 675 | "cell_type": "code", 676 | "execution_count": null, 677 | "metadata": {}, 678 | "outputs": [], 679 | "source": [ 680 | "# TODO - Read about Recursion \n", 681 | "\n", 682 | "# Fibonacci 0,1,1,2,3,5,8,13" 683 | ] 684 | }, 685 | { 686 | "cell_type": "code", 687 | "execution_count": 85, 688 | "metadata": {}, 689 | "outputs": [ 690 | { 691 | "ename": "AssertionError", 692 | "evalue": "", 693 | "output_type": "error", 694 | "traceback": [ 695 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 696 | "\u001b[1;31mAssertionError\u001b[0m Traceback (most recent call last)", 697 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 13\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mfib\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mi\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 14\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 15\u001b[1;33m \u001b[0mprint_fib\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m-\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 16\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n", 698 | "\u001b[1;32m\u001b[0m in \u001b[0;36mprint_fib\u001b[1;34m(num)\u001b[0m\n\u001b[0;32m 8\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 9\u001b[0m \u001b[1;32mdef\u001b[0m \u001b[0mprint_fib\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mnum\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 10\u001b[1;33m \u001b[1;32massert\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mnum\u001b[0m \u001b[1;33m>\u001b[0m \u001b[1;36m0\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 11\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Fibonacci sequence:\"\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 12\u001b[0m \u001b[1;32mfor\u001b[0m \u001b[0mi\u001b[0m \u001b[1;32min\u001b[0m \u001b[0mrange\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mnum\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n", 699 | "\u001b[1;31mAssertionError\u001b[0m: " 700 | ] 701 | } 702 | ], 703 | "source": [ 704 | "# another example on assert\n", 705 | "\n", 706 | "def fib(n):\n", 707 | " if n == 0 or n ==1:\n", 708 | " return n\n", 709 | " else:\n", 710 | " return fib(n-1)+fib(n-2)\n", 711 | " \n", 712 | "def print_fib(num):\n", 713 | " assert(num > 0)\n", 714 | " print(\"Fibonacci sequence:\")\n", 715 | " for i in range(num):\n", 716 | " print(fib(i))\n", 717 | " \n", 718 | "print_fib(-1)\n", 719 | " " 720 | ] 721 | }, 722 | { 723 | "cell_type": "markdown", 724 | "metadata": {}, 725 | "source": [ 726 | "# `try/except` Statement syntax" 727 | ] 728 | }, 729 | { 730 | "cell_type": "markdown", 731 | "metadata": {}, 732 | "source": [ 733 | "```\n", 734 | "try:\n", 735 | " statements # Run this main action first\n", 736 | "except name1: \n", 737 | " # Run if name1 is raised during try block\n", 738 | " statements\n", 739 | "except (name2, name3): \n", 740 | " # Run if any of these exceptions occur\n", 741 | " statements \n", 742 | "except name4 as var: \n", 743 | " # Run if name4 is raised, assign instance raised to var \n", 744 | " statements\n", 745 | "except: # Run for all other exceptions raised\n", 746 | " statements\n", 747 | "else:\n", 748 | " statements # Run if no exception was raised during try block\n", 749 | "```" 750 | ] 751 | }, 752 | { 753 | "cell_type": "code", 754 | "execution_count": null, 755 | "metadata": {}, 756 | "outputs": [], 757 | "source": [ 758 | "# Try & Except - Example 1\n", 759 | "\n", 760 | "id = int(input())\n" 761 | ] 762 | }, 763 | { 764 | "cell_type": "code", 765 | "execution_count": 26, 766 | "metadata": {}, 767 | "outputs": [ 768 | { 769 | "name": "stdout", 770 | "output_type": "stream", 771 | "text": [ 772 | "The entry is a\n", 773 | "Oops! occurred.\n", 774 | "Next entry.\n", 775 | "\n", 776 | "The entry is 0\n", 777 | "Oops! occurred.\n", 778 | "Next entry.\n", 779 | "\n", 780 | "The entry is 2\n", 781 | "The reciprocal of 2 is 0.5\n" 782 | ] 783 | } 784 | ], 785 | "source": [ 786 | "# Try & Except - Example 2\n", 787 | "import sys\n", 788 | "\n", 789 | "randomList = ['a', 0, 2]\n", 790 | "\n", 791 | "for entry in randomList:\n", 792 | " try:\n", 793 | " print(\"The entry is\", entry)\n", 794 | " r = 1/int(entry)\n", 795 | " break\n", 796 | " except Exception as e:\n", 797 | " print(\"Oops!\", e.__class__, \"occurred.\")\n", 798 | " print(\"Next entry.\")\n", 799 | " print()\n", 800 | "print(\"The reciprocal of\", entry, \"is\", r)" 801 | ] 802 | }, 803 | { 804 | "cell_type": "code", 805 | "execution_count": null, 806 | "metadata": {}, 807 | "outputs": [], 808 | "source": [ 809 | "# Try & Except - Example 3\n", 810 | "\n", 811 | "try:\n", 812 | " with open('file.log', 'r') as file:\n", 813 | " lines = file.readlines()\n", 814 | " print(lines[1])\n", 815 | "except FileNotFoundError as fnf_error:\n", 816 | " raise\n", 817 | "except IndexError:\n", 818 | " print(\"list index out of error\")" 819 | ] 820 | }, 821 | { 822 | "cell_type": "markdown", 823 | "metadata": {}, 824 | "source": [ 825 | "# `try/finally` Statement" 826 | ] 827 | }, 828 | { 829 | "cell_type": "markdown", 830 | "metadata": {}, 831 | "source": [ 832 | "The other flavor of the try statement is a specialization that has to do with finalization (a.k.a. termination) actions. If a finally clause is included in a try, Python will always run its block of statements “on the way out” of the try statement, whether an exception occurred while the try block was running or not. \n", 833 | "\n", 834 | "In it's general form, it is:\n", 835 | "\n", 836 | "```\n", 837 | "try:\n", 838 | " statements # Run this action first \n", 839 | "finally:\n", 840 | " statements # Always run this code on the way out\n", 841 | "```" 842 | ] 843 | }, 844 | { 845 | "cell_type": "code", 846 | "execution_count": 3, 847 | "metadata": { 848 | "scrolled": true 849 | }, 850 | "outputs": [], 851 | "source": [ 852 | "try:\n", 853 | " f = open(\"Session3-Exceptions.ipynb\", encoding = 'utf-8')\n", 854 | " # perform file operations\n", 855 | "except:\n", 856 | " pass\n", 857 | "finally:\n", 858 | " f.close()" 859 | ] 860 | }, 861 | { 862 | "cell_type": "markdown", 863 | "metadata": {}, 864 | "source": [ 865 | "" 866 | ] 867 | }, 868 | { 869 | "cell_type": "markdown", 870 | "metadata": {}, 871 | "source": [ 872 | "## User Defined Exceptions" 873 | ] 874 | }, 875 | { 876 | "cell_type": "code", 877 | "execution_count": null, 878 | "metadata": {}, 879 | "outputs": [], 880 | "source": [ 881 | "# Example 1\n", 882 | "\n", 883 | "class AlreadyGotOne(Exception):\n", 884 | " pass\n", 885 | "\n", 886 | "def my_func():\n", 887 | " raise AlreadyGotOne()\n", 888 | " " 889 | ] 890 | }, 891 | { 892 | "cell_type": "code", 893 | "execution_count": 63, 894 | "metadata": {}, 895 | "outputs": [ 896 | { 897 | "name": "stdout", 898 | "output_type": "stream", 899 | "text": [ 900 | "got exception\n" 901 | ] 902 | } 903 | ], 904 | "source": [ 905 | "try:\n", 906 | " my_func()\n", 907 | "except AlreadyGotOne:\n", 908 | " print('got exception')" 909 | ] 910 | }, 911 | { 912 | "cell_type": "code", 913 | "execution_count": 64, 914 | "metadata": { 915 | "scrolled": true 916 | }, 917 | "outputs": [ 918 | { 919 | "ename": "Career", 920 | "evalue": "So I became a waiter of Engineer", 921 | "output_type": "error", 922 | "traceback": [ 923 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 924 | "\u001b[1;31mCareer\u001b[0m Traceback (most recent call last)", 925 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 8\u001b[0m \u001b[1;32mreturn\u001b[0m \u001b[1;34m'So I became a waiter of {}'\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mformat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mself\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0m_job\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 9\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 10\u001b[1;33m \u001b[1;32mraise\u001b[0m \u001b[0mCareer\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m'Engineer'\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 926 | "\u001b[1;31mCareer\u001b[0m: So I became a waiter of Engineer" 927 | ] 928 | } 929 | ], 930 | "source": [ 931 | "# Example 2\n", 932 | "class Career(Exception):\n", 933 | " \n", 934 | " def __init__(self, job, *args, **kwargs):\n", 935 | " super(Career, self).__init__(*args, **kwargs)\n", 936 | " self._job = job\n", 937 | " \n", 938 | " def __str__(self): \n", 939 | " return 'So I became a waiter of {}'.format(self._job)\n", 940 | " \n", 941 | "raise Career('Engineer')" 942 | ] 943 | }, 944 | { 945 | "cell_type": "code", 946 | "execution_count": 65, 947 | "metadata": {}, 948 | "outputs": [ 949 | { 950 | "name": "stdout", 951 | "output_type": "stream", 952 | "text": [ 953 | "Enter salary amount: 12\n" 954 | ] 955 | }, 956 | { 957 | "ename": "SalaryNotInRangeError", 958 | "evalue": "Salary is not in (5000, 15000) range", 959 | "output_type": "error", 960 | "traceback": [ 961 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 962 | "\u001b[1;31mSalaryNotInRangeError\u001b[0m Traceback (most recent call last)", 963 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 10\u001b[0m \u001b[0msalary\u001b[0m \u001b[1;33m=\u001b[0m \u001b[0mint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0minput\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Enter salary amount: \"\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 11\u001b[0m \u001b[1;32mif\u001b[0m \u001b[1;32mnot\u001b[0m \u001b[1;36m5000\u001b[0m \u001b[1;33m<\u001b[0m \u001b[0msalary\u001b[0m \u001b[1;33m<\u001b[0m \u001b[1;36m15000\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 12\u001b[1;33m \u001b[1;32mraise\u001b[0m \u001b[0mSalaryNotInRangeError\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0msalary\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 964 | "\u001b[1;31mSalaryNotInRangeError\u001b[0m: Salary is not in (5000, 15000) range" 965 | ] 966 | } 967 | ], 968 | "source": [ 969 | "# Example 3\n", 970 | "\n", 971 | "class SalaryNotInRangeError(Exception):\n", 972 | " def __init__(self, salary, message=\"Salary is not in (5000, 15000) range\"):\n", 973 | " self.salary = salary\n", 974 | " self.message = message\n", 975 | " super().__init__(self.message)\n", 976 | "\n", 977 | "\n", 978 | "salary = int(input(\"Enter salary amount: \"))\n", 979 | "if not 5000 < salary < 15000:\n", 980 | " raise SalaryNotInRangeError(salary)" 981 | ] 982 | } 983 | ], 984 | "metadata": { 985 | "kernelspec": { 986 | "display_name": "Python 3", 987 | "language": "python", 988 | "name": "python3" 989 | }, 990 | "language_info": { 991 | "codemirror_mode": { 992 | "name": "ipython", 993 | "version": 3 994 | }, 995 | "file_extension": ".py", 996 | "mimetype": "text/x-python", 997 | "name": "python", 998 | "nbconvert_exporter": "python", 999 | "pygments_lexer": "ipython3", 1000 | "version": "3.7.5" 1001 | } 1002 | }, 1003 | "nbformat": 4, 1004 | "nbformat_minor": 1 1005 | } 1006 | -------------------------------------------------------------------------------- /notebooks/4_more_on_functions.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": { 6 | "slideshow": { 7 | "slide_type": "slide" 8 | } 9 | }, 10 | "source": [ 11 | "More on Functions\n", 12 | "===" 13 | ] 14 | }, 15 | { 16 | "cell_type": "markdown", 17 | "metadata": { 18 | "slideshow": { 19 | "slide_type": "fragment" 20 | } 21 | }, 22 | "source": [ 23 | "Earlier we learned the most bare-boned versions of functions. In this section we will learn more general concepts about functions, such as how to use functions to return values, and how to pass different kinds of data structures between functions." 24 | ] 25 | }, 26 | { 27 | "cell_type": "markdown", 28 | "metadata": { 29 | "slideshow": { 30 | "slide_type": "slide" 31 | } 32 | }, 33 | "source": [ 34 | "Default argument values\n", 35 | "===" 36 | ] 37 | }, 38 | { 39 | "cell_type": "code", 40 | "execution_count": 2, 41 | "metadata": { 42 | "slideshow": { 43 | "slide_type": "fragment" 44 | } 45 | }, 46 | "outputs": [ 47 | { 48 | "name": "stdout", 49 | "output_type": "stream", 50 | "text": [ 51 | "\n", 52 | " Hello Santosh, hope you are finding this training useful!\n", 53 | "\n", 54 | " Hello Sunil, hope you are finding this training useful!\n", 55 | "\n", 56 | " Hello Mahi, hope you are finding this training useful!\n" 57 | ] 58 | } 59 | ], 60 | "source": [ 61 | "def hello_there(name):\n", 62 | " print(\"\\n Hello {}, hope you are finding this training useful!\".format(name))\n", 63 | " \n", 64 | "hello_there('Santosh')\n", 65 | "hello_there('Sunil')\n", 66 | "hello_there('Mahi')" 67 | ] 68 | }, 69 | { 70 | "cell_type": "code", 71 | "execution_count": 1, 72 | "metadata": {}, 73 | "outputs": [ 74 | { 75 | "name": "stdout", 76 | "output_type": "stream", 77 | "text": [ 78 | "My name is Sanchit Balchandani\n" 79 | ] 80 | } 81 | ], 82 | "source": [ 83 | "last_name = \"Balchandani\"\n", 84 | "a = \"My name is Sanchit {}\".format(last_name)\n", 85 | "print(a)" 86 | ] 87 | }, 88 | { 89 | "cell_type": "code", 90 | "execution_count": 2, 91 | "metadata": {}, 92 | "outputs": [ 93 | { 94 | "name": "stdout", 95 | "output_type": "stream", 96 | "text": [ 97 | "My Name is Sanchit Balchandani\n" 98 | ] 99 | } 100 | ], 101 | "source": [ 102 | "print(f\"My Name is Sanchit {last_name}\")" 103 | ] 104 | }, 105 | { 106 | "cell_type": "code", 107 | "execution_count": 4, 108 | "metadata": { 109 | "slideshow": { 110 | "slide_type": "fragment" 111 | } 112 | }, 113 | "outputs": [ 114 | { 115 | "name": "stdout", 116 | "output_type": "stream", 117 | "text": [ 118 | "\n", 119 | " Hello Santosh, hope you are finding this training useful!\n", 120 | "\n", 121 | " Hello Sunil, hope you are finding this training useful!\n" 122 | ] 123 | }, 124 | { 125 | "ename": "TypeError", 126 | "evalue": "hello_there() missing 1 required positional argument: 'name'", 127 | "output_type": "error", 128 | "traceback": [ 129 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 130 | "\u001b[1;31mTypeError\u001b[0m Traceback (most recent call last)", 131 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 7\u001b[0m \u001b[0mhello_there\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m'Santosh'\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 8\u001b[0m \u001b[0mhello_there\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m'Sunil'\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 9\u001b[1;33m \u001b[0mhello_there\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 132 | "\u001b[1;31mTypeError\u001b[0m: hello_there() missing 1 required positional argument: 'name'" 133 | ] 134 | } 135 | ], 136 | "source": [ 137 | "# same function fails if you don't pass the value\n", 138 | "def hello_there(name):\n", 139 | " if not name:\n", 140 | " print(\"lkjdljfl\")\n", 141 | " print(\"\\n Hello {}, hope you are finding this training useful!\".format(name))\n", 142 | " \n", 143 | "hello_there('Santosh')\n", 144 | "hello_there('Sunil')\n", 145 | "hello_there()" 146 | ] 147 | }, 148 | { 149 | "cell_type": "markdown", 150 | "metadata": { 151 | "slideshow": { 152 | "slide_type": "subslide" 153 | } 154 | }, 155 | "source": [ 156 | "That makes sense; the function needs to have a name in order to do its work, so without a name it is stuck.\n", 157 | "\n", 158 | "If you want your function to do something by default, even if no information is passed to it, you can do so by giving your arguments default values. You do this by specifying the default values when you define the function:" 159 | ] 160 | }, 161 | { 162 | "cell_type": "code", 163 | "execution_count": 5, 164 | "metadata": { 165 | "slideshow": { 166 | "slide_type": "fragment" 167 | } 168 | }, 169 | "outputs": [ 170 | { 171 | "name": "stdout", 172 | "output_type": "stream", 173 | "text": [ 174 | "\n", 175 | " Hello Santosh, hope you are finding this training useful!\n", 176 | "\n", 177 | " Hello Sunil, hope you are finding this training useful!\n", 178 | "\n", 179 | " Hello EveryOne, hope you are finding this training useful!\n" 180 | ] 181 | } 182 | ], 183 | "source": [ 184 | "def hello_there(name=\"EveryOne\"):\n", 185 | " print(\"\\n Hello {}, hope you are finding this training useful!\".format(name))\n", 186 | " \n", 187 | "hello_there('Santosh')\n", 188 | "hello_there('Sunil')\n", 189 | "hello_there()" 190 | ] 191 | }, 192 | { 193 | "cell_type": "markdown", 194 | "metadata": { 195 | "slideshow": { 196 | "slide_type": "fragment" 197 | } 198 | }, 199 | "source": [ 200 | "This is particularly useful when you have a number of arguments in your function, and some of those arguments almost always have the same value. This allows people who use the function to only specify the values that are unique to their use of the function." 201 | ] 202 | }, 203 | { 204 | "cell_type": "markdown", 205 | "metadata": { 206 | "slideshow": { 207 | "slide_type": "slide" 208 | } 209 | }, 210 | "source": [ 211 | "Positional Arguments\n", 212 | "===" 213 | ] 214 | }, 215 | { 216 | "cell_type": "markdown", 217 | "metadata": { 218 | "slideshow": { 219 | "slide_type": "fragment" 220 | } 221 | }, 222 | "source": [ 223 | "Much of what you will have to learn about using functions involves how to pass values from your calling statement to the function itself. The example we just looked at is pretty simple, in that the function only needed one argument in order to do its work. Let's take a look at a function that requires two arguments to do its work." 224 | ] 225 | }, 226 | { 227 | "cell_type": "code", 228 | "execution_count": 7, 229 | "metadata": { 230 | "scrolled": true, 231 | "slideshow": { 232 | "slide_type": "fragment" 233 | } 234 | }, 235 | "outputs": [ 236 | { 237 | "name": "stdout", 238 | "output_type": "stream", 239 | "text": [ 240 | "Nick name: Professor\n", 241 | "First name: Álvaro\n", 242 | "Last name: Morte\n", 243 | "Age: 45\n", 244 | "\n", 245 | "\n", 246 | "Nick name: Tokyo\n", 247 | "First name: Úrsula\n", 248 | "Last name: Corberó\n", 249 | "Age: 30\n", 250 | "\n", 251 | "\n", 252 | "Nick name: Berlin\n", 253 | "First name: Pedro González\n", 254 | "Last name: Alonso\n", 255 | "Age: 48\n", 256 | "\n", 257 | "\n" 258 | ] 259 | } 260 | ], 261 | "source": [ 262 | "def describe_money_heist_character(nick_name, first_name, last_name, age):\n", 263 | " print(\"Nick name: {}\".format(nick_name.title()))\n", 264 | " print(\"First name: {}\".format(first_name.title()))\n", 265 | " print(\"Last name: {}\".format(last_name.title()))\n", 266 | " print(\"Age: {}\".format(age))\n", 267 | " print(\"\\n\")\n", 268 | "\n", 269 | "describe_money_heist_character('Professor', 'Álvaro', 'Morte', 45)\n", 270 | "describe_money_heist_character('Tokyo', 'Úrsula', 'Corberó', 30)\n", 271 | "describe_money_heist_character('Berlin', 'Pedro González', 'Alonso', 48)" 272 | ] 273 | }, 274 | { 275 | "cell_type": "markdown", 276 | "metadata": { 277 | "slideshow": { 278 | "slide_type": "subslide" 279 | } 280 | }, 281 | "source": [ 282 | "The arguments in this function are `nick_name`, `first_name`, `last_name`, and `age`. These are called *positional arguments* because Python knows which value to assign to each by the order in which you give the function values. In the calling line\n", 283 | "\n", 284 | " describe_character('Professor', 'Álvaro', 'Morte', 45)\n", 285 | "\n", 286 | "we send the values to the function. Python matches the first value with the first argument `nick_name`. It matches the second value with the second argument `first_name`. Finally it matches the last value with the third argument `age`.\n", 287 | "\n", 288 | "This is pretty straightforward, but it means we have to make sure to get the arguments in the right order." 289 | ] 290 | }, 291 | { 292 | "cell_type": "markdown", 293 | "metadata": { 294 | "slideshow": { 295 | "slide_type": "subslide" 296 | } 297 | }, 298 | "source": [ 299 | "If we mess up the order, we get nonsense results or an error:" 300 | ] 301 | }, 302 | { 303 | "cell_type": "code", 304 | "execution_count": 8, 305 | "metadata": { 306 | "slideshow": { 307 | "slide_type": "fragment" 308 | } 309 | }, 310 | "outputs": [ 311 | { 312 | "name": "stdout", 313 | "output_type": "stream", 314 | "text": [ 315 | "Nick name: Professor\n", 316 | "First name: Álvaro\n", 317 | "Last name: Morte\n", 318 | "Age: 45\n", 319 | "\n", 320 | "\n", 321 | "Nick name: Tokyo\n", 322 | "First name: Úrsula\n", 323 | "Last name: Corberó\n", 324 | "Age: 30\n", 325 | "\n", 326 | "\n" 327 | ] 328 | }, 329 | { 330 | "ename": "AttributeError", 331 | "evalue": "'int' object has no attribute 'title'", 332 | "output_type": "error", 333 | "traceback": [ 334 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 335 | "\u001b[1;31mAttributeError\u001b[0m Traceback (most recent call last)", 336 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 8\u001b[0m \u001b[0mdescribe_money_heist_character\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m'Professor'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Álvaro'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Morte'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m45\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 9\u001b[0m \u001b[0mdescribe_money_heist_character\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m'Tokyo'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Úrsula'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Corberó'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m30\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 10\u001b[1;33m \u001b[0mdescribe_money_heist_character\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;36m48\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Berlin'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Pedro González'\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;34m'Alonso'\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 337 | "\u001b[1;32m\u001b[0m in \u001b[0;36mdescribe_money_heist_character\u001b[1;34m(nick_name, first_name, last_name, age)\u001b[0m\n\u001b[0;32m 1\u001b[0m \u001b[1;32mdef\u001b[0m \u001b[0mdescribe_money_heist_character\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mnick_name\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mfirst_name\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mlast_name\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0mage\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 2\u001b[1;33m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Nick name: {}\"\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mformat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mnick_name\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mtitle\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 3\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"First name: {}\"\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mformat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mfirst_name\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mtitle\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 4\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Last name: {}\"\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mformat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mlast_name\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mtitle\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 5\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Age: {}\"\u001b[0m\u001b[1;33m.\u001b[0m\u001b[0mformat\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0mage\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n", 338 | "\u001b[1;31mAttributeError\u001b[0m: 'int' object has no attribute 'title'" 339 | ] 340 | } 341 | ], 342 | "source": [ 343 | "def describe_money_heist_character(nick_name, first_name, last_name, age):\n", 344 | " \"\"\"\n", 345 | " nick_name: str\n", 346 | " first_name: str\n", 347 | " last_name: str\n", 348 | " \n", 349 | " return:Dict/Str/Int\n", 350 | " \n", 351 | " \"\"\"\n", 352 | " print(\"Nick name: {}\".format(nick_name.title()))\n", 353 | " print(\"First name: {}\".format(first_name.title()))\n", 354 | " print(\"Last name: {}\".format(last_name.title()))\n", 355 | " print(\"Age: {}\".format(age))\n", 356 | " print(\"\\n\")\n", 357 | "\n", 358 | "describe_money_heist_character('Professor', 'Álvaro', 'Morte', 45)\n", 359 | "describe_money_heist_character('Tokyo', 'Úrsula', 'Corberó', 30)\n", 360 | "describe_money_heist_character(48, 'Berlin', 'Pedro González', 'Alonso')" 361 | ] 362 | }, 363 | { 364 | "cell_type": "markdown", 365 | "metadata": { 366 | "slideshow": { 367 | "slide_type": "subslide" 368 | } 369 | }, 370 | "source": [ 371 | "Keyword arguments\n", 372 | "===\n", 373 | "Python allows us to use a syntax called *keyword arguments*. In this case, we can give the arguments in any order when we call the function, as long as we use the name of the arguments in our calling statement. Here is how the previous code can be made to work using keyword arguments:" 374 | ] 375 | }, 376 | { 377 | "cell_type": "code", 378 | "execution_count": 12, 379 | "metadata": { 380 | "slideshow": { 381 | "slide_type": "subslide" 382 | } 383 | }, 384 | "outputs": [ 385 | { 386 | "name": "stdout", 387 | "output_type": "stream", 388 | "text": [ 389 | "Nick name: Professor\n", 390 | "First name: Álvaro\n", 391 | "Last name: Morte\n", 392 | "This guy is immortal\n", 393 | "\n", 394 | "\n", 395 | "Nick name: Professor\n", 396 | "First name: Álvaro\n", 397 | "Last name: Morte\n", 398 | "This guy is immortal\n", 399 | "\n", 400 | "\n", 401 | "Nick name: Tokyo\n", 402 | "First name: Úrsula\n", 403 | "Last name: Corberó\n", 404 | "Age: 30\n", 405 | "\n", 406 | "\n", 407 | "Nick name: Berlin\n", 408 | "First name: Pedro González\n", 409 | "Last name: Alonso\n", 410 | "This guy is immortal\n", 411 | "This character has died :(\n", 412 | "\n", 413 | "\n" 414 | ] 415 | } 416 | ], 417 | "source": [ 418 | "def describe_money_heist_character(nick_name, first_name, last_name, age=None, died=None):\n", 419 | " print(\"Nick name: {}\".format(nick_name.title()))\n", 420 | " print(\"First name: {}\".format(first_name.title()))\n", 421 | " print(\"Last name: {}\".format(last_name.title()))\n", 422 | " if age and isinstance(age, int):\n", 423 | " print(\"Age: {}\".format(age))\n", 424 | " else:\n", 425 | " print(\"This guy is immortal\")\n", 426 | " if died:\n", 427 | " print(\"This character has died :(\")\n", 428 | " print(\"\\n\")\n", 429 | "\n", 430 | "describe_money_heist_character('Professor', 'Álvaro', 'Morte', age=\"Sanchit\")\n", 431 | "describe_money_heist_character('Professor', 'Álvaro', 'Morte')\n", 432 | "describe_money_heist_character('Tokyo', 'Úrsula', 'Corberó', age=30)\n", 433 | "describe_money_heist_character('Berlin', 'Pedro González', 'Alonso', died=True)" 434 | ] 435 | }, 436 | { 437 | "cell_type": "markdown", 438 | "metadata": { 439 | "slideshow": { 440 | "slide_type": "slide" 441 | } 442 | }, 443 | "source": [ 444 | "Accepting an arbitrary number of arguments\n", 445 | "===" 446 | ] 447 | }, 448 | { 449 | "cell_type": "code", 450 | "execution_count": 13, 451 | "metadata": { 452 | "slideshow": { 453 | "slide_type": "subslide" 454 | } 455 | }, 456 | "outputs": [ 457 | { 458 | "name": "stdout", 459 | "output_type": "stream", 460 | "text": [ 461 | "The sum of your numbers is 3.\n", 462 | "The sum of your numbers is 1.\n", 463 | "The sum of your numbers is -1.\n" 464 | ] 465 | } 466 | ], 467 | "source": [ 468 | "def add(num_1, num_2):\n", 469 | " sum = num_1 + num_2\n", 470 | " print(\"The sum of your numbers is {}.\".format(sum))\n", 471 | " \n", 472 | "# Let's add some numbers.\n", 473 | "add(1, 2)\n", 474 | "add(-1, 2)\n", 475 | "add(1, -2)" 476 | ] 477 | }, 478 | { 479 | "cell_type": "markdown", 480 | "metadata": { 481 | "slideshow": { 482 | "slide_type": "subslide" 483 | } 484 | }, 485 | "source": [ 486 | "This function appears to work well. But what if we pass it three numbers, which is a perfectly reasonable thing to do mathematically?" 487 | ] 488 | }, 489 | { 490 | "cell_type": "code", 491 | "execution_count": 14, 492 | "metadata": { 493 | "slideshow": { 494 | "slide_type": "fragment" 495 | } 496 | }, 497 | "outputs": [ 498 | { 499 | "ename": "TypeError", 500 | "evalue": "add() takes 2 positional arguments but 3 were given", 501 | "output_type": "error", 502 | "traceback": [ 503 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 504 | "\u001b[1;31mTypeError\u001b[0m Traceback (most recent call last)", 505 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 4\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 5\u001b[0m \u001b[1;31m# Let's add some numbers.\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 6\u001b[1;33m \u001b[0madd\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m2\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m3\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m", 506 | "\u001b[1;31mTypeError\u001b[0m: add() takes 2 positional arguments but 3 were given" 507 | ] 508 | } 509 | ], 510 | "source": [ 511 | "def add(num_1, num_2):\n", 512 | " sum = num_1 + num_2\n", 513 | " print(\"The sum of your numbers is {}.\".format(sum))\n", 514 | " \n", 515 | "# Let's add some numbers.\n", 516 | "add(1, 2, 3)" 517 | ] 518 | }, 519 | { 520 | "cell_type": "code", 521 | "execution_count": 16, 522 | "metadata": { 523 | "slideshow": { 524 | "slide_type": "fragment" 525 | } 526 | }, 527 | "outputs": [ 528 | { 529 | "name": "stdout", 530 | "output_type": "stream", 531 | "text": [ 532 | "\n", 533 | "arg_1: 1\n", 534 | "arg_2: 2\n", 535 | "\n", 536 | "arg_1: 1\n", 537 | "arg_2: 2\n", 538 | "arg_3 value: 3\n", 539 | "\n", 540 | "arg_1: 1\n", 541 | "arg_2: 2\n", 542 | "arg_3 value: 3\n", 543 | "arg_3 value: 4\n", 544 | "\n", 545 | "arg_1: 1\n", 546 | "arg_2: 2\n", 547 | "arg_3 value: 3\n", 548 | "arg_3 value: 4\n", 549 | "arg_3 value: 5\n", 550 | "arg_3 value: 6\n", 551 | "arg_3 value: 7\n", 552 | "arg_3 value: 8\n", 553 | "arg_3 value: 9\n" 554 | ] 555 | } 556 | ], 557 | "source": [ 558 | "#*args , **kwargs\n", 559 | "def example_function(arg_1, arg_2, *arg_3):\n", 560 | " # Let's look at the argument values.\n", 561 | " print('\\narg_1:', arg_1)\n", 562 | " print('arg_2:', arg_2)\n", 563 | " for value in arg_3:\n", 564 | " print('arg_3 value:', value)\n", 565 | "\n", 566 | "example_function(1, 2)\n", 567 | "example_function(1, 2, 3)\n", 568 | "example_function(1, 2, 3, 4)\n", 569 | "example_function(1, 2, 3, 4, 5,6,7,8,9)" 570 | ] 571 | }, 572 | { 573 | "cell_type": "markdown", 574 | "metadata": { 575 | "slideshow": { 576 | "slide_type": "subslide" 577 | } 578 | }, 579 | "source": [ 580 | "We can now rewrite the add() function to accept two or more arguments, and print the sum of those numbers:" 581 | ] 582 | }, 583 | { 584 | "cell_type": "code", 585 | "execution_count": 17, 586 | "metadata": { 587 | "slideshow": { 588 | "slide_type": "fragment" 589 | } 590 | }, 591 | "outputs": [ 592 | { 593 | "name": "stdout", 594 | "output_type": "stream", 595 | "text": [ 596 | "The sum of your numbers is 6.\n" 597 | ] 598 | } 599 | ], 600 | "source": [ 601 | "def add(*nums):\n", 602 | " \"\"\"This function adds the given numbers together and prints the sum.\"\"\"\n", 603 | " # Print the results.\n", 604 | " print(\"The sum of your numbers is {}.\".format(sum(nums)))\n", 605 | " \n", 606 | "# Let's add some numbers.\n", 607 | "add(1, 2, 3)" 608 | ] 609 | }, 610 | { 611 | "cell_type": "code", 612 | "execution_count": 19, 613 | "metadata": { 614 | "slideshow": { 615 | "slide_type": "fragment" 616 | } 617 | }, 618 | "outputs": [ 619 | { 620 | "name": "stdout", 621 | "output_type": "stream", 622 | "text": [ 623 | "The sum of your numbers is 3.\n", 624 | "The sum of your numbers is 6.\n", 625 | "The sum of your numbers is 10.\n", 626 | "The sum of your numbers is 15.\n" 627 | ] 628 | } 629 | ], 630 | "source": [ 631 | "def add(num_1, num_2, *nums):\n", 632 | " sum = num_1 + num_2\n", 633 | " \n", 634 | " for num in nums:\n", 635 | " sum = sum + num\n", 636 | " \n", 637 | " print(f\"The sum of your numbers is {sum}.\")\n", 638 | "\n", 639 | "add(1, 2)\n", 640 | "add(1, 2, 3)\n", 641 | "add(1, 2, 3, 4)\n", 642 | "add(1, 2, 3, 4, 5)" 643 | ] 644 | }, 645 | { 646 | "cell_type": "markdown", 647 | "metadata": { 648 | "slideshow": { 649 | "slide_type": "subslide" 650 | } 651 | }, 652 | "source": [ 653 | "Accepting an arbitrary number of keyword arguments\n", 654 | "---\n", 655 | "Python also provides a syntax for accepting an arbitrary number of keyword arguments. The syntax looks like this:" 656 | ] 657 | }, 658 | { 659 | "cell_type": "code", 660 | "execution_count": 18, 661 | "metadata": { 662 | "scrolled": false 663 | }, 664 | "outputs": [ 665 | { 666 | "name": "stdout", 667 | "output_type": "stream", 668 | "text": [ 669 | "1 2 4 5\n", 670 | "{}\n", 671 | "1 3\n", 672 | "{'value': 1, 'name': 5}\n", 673 | "value : 1\n", 674 | "name : 5\n" 675 | ] 676 | } 677 | ], 678 | "source": [ 679 | "def example_function(*args, **kwargs):\n", 680 | " print(*args)\n", 681 | " print(kwargs)\n", 682 | " for k, v in kwargs.items():\n", 683 | " print(k,':', v)\n", 684 | " \n", 685 | "example_function(1, 2, 4, 5)\n", 686 | "example_function(1, 3, value=1, name=5)\n" 687 | ] 688 | }, 689 | { 690 | "cell_type": "code", 691 | "execution_count": null, 692 | "metadata": {}, 693 | "outputs": [], 694 | "source": [] 695 | } 696 | ], 697 | "metadata": { 698 | "kernelspec": { 699 | "display_name": "Python 3", 700 | "language": "python", 701 | "name": "python3" 702 | }, 703 | "language_info": { 704 | "codemirror_mode": { 705 | "name": "ipython", 706 | "version": 3 707 | }, 708 | "file_extension": ".py", 709 | "mimetype": "text/x-python", 710 | "name": "python", 711 | "nbconvert_exporter": "python", 712 | "pygments_lexer": "ipython3", 713 | "version": "3.7.5" 714 | } 715 | }, 716 | "nbformat": 4, 717 | "nbformat_minor": 1 718 | } 719 | -------------------------------------------------------------------------------- /notebooks/5_map_reduce_filter_lambda_scoping.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "### What are lambda functions in Python?" 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "In Python, an anonymous function is a function that is defined without a name.\n", 15 | "\n", 16 | "While normal functions are defined using the def keyword in Python, anonymous functions are defined using the lambda keyword.\n", 17 | "\n", 18 | "Hence, anonymous functions are also called lambda functions.\n", 19 | "\n", 20 | "\n", 21 | "Syntax of Lambda Function in python
\n", 22 | "```lambda arguments: expression```" 23 | ] 24 | }, 25 | { 26 | "cell_type": "code", 27 | "execution_count": 1, 28 | "metadata": {}, 29 | "outputs": [ 30 | { 31 | "name": "stdout", 32 | "output_type": "stream", 33 | "text": [ 34 | "10\n" 35 | ] 36 | } 37 | ], 38 | "source": [ 39 | "# use of lambda functions - Example 1\n", 40 | "double = lambda x: x * 2\n", 41 | "\n", 42 | "print(double(5))" 43 | ] 44 | }, 45 | { 46 | "cell_type": "code", 47 | "execution_count": 3, 48 | "metadata": { 49 | "scrolled": true 50 | }, 51 | "outputs": [ 52 | { 53 | "name": "stdout", 54 | "output_type": "stream", 55 | "text": [ 56 | "13\n" 57 | ] 58 | } 59 | ], 60 | "source": [ 61 | "# use of lambda functions - Example 2\n", 62 | "add_square = lambda x,y: x**2+y**2\n", 63 | "\n", 64 | "print(add_square(2,3))" 65 | ] 66 | }, 67 | { 68 | "cell_type": "markdown", 69 | "metadata": {}, 70 | "source": [ 71 | "## Map function\n", 72 | "\n", 73 | "Basic Syntax
\n", 74 | "```map(function_object, iterable1, iterable2,...)```" 75 | ] 76 | }, 77 | { 78 | "cell_type": "code", 79 | "execution_count": 4, 80 | "metadata": {}, 81 | "outputs": [ 82 | { 83 | "data": { 84 | "text/plain": [ 85 | "" 86 | ] 87 | }, 88 | "execution_count": 4, 89 | "metadata": {}, 90 | "output_type": "execute_result" 91 | } 92 | ], 93 | "source": [ 94 | "# Example 1\n", 95 | "\n", 96 | "def multiply2(x):\n", 97 | " return x * 2\n", 98 | " \n", 99 | "map(multiply2, [1, 2, 3, 4]) # Output [2, 4, 6, 8]" 100 | ] 101 | }, 102 | { 103 | "cell_type": "code", 104 | "execution_count": 5, 105 | "metadata": {}, 106 | "outputs": [ 107 | { 108 | "data": { 109 | "text/plain": [ 110 | "" 111 | ] 112 | }, 113 | "execution_count": 5, 114 | "metadata": {}, 115 | "output_type": "execute_result" 116 | } 117 | ], 118 | "source": [ 119 | "# Example 2\n", 120 | "\n", 121 | "map(lambda x : x*2, [1, 2, 3, 4]) #Output [2, 4, 6, 8]\n" 122 | ] 123 | }, 124 | { 125 | "cell_type": "code", 126 | "execution_count": 9, 127 | "metadata": {}, 128 | "outputs": [ 129 | { 130 | "name": "stdout", 131 | "output_type": "stream", 132 | "text": [ 133 | "['python', 'java']\n", 134 | "[100, 80]\n", 135 | "[True, False]\n" 136 | ] 137 | } 138 | ], 139 | "source": [ 140 | "# Example 3\n", 141 | "\n", 142 | "dict_a = [{'name': 'python', 'points': 10}, {'name': 'java', 'points': 8}]\n", 143 | " \n", 144 | "print(list(map(lambda x : x['name'], dict_a)))\n", 145 | " \n", 146 | "print(list(map(lambda x : x['points']*10, dict_a)))\n", 147 | "\n", 148 | "print(list(map(lambda x : x['name'] == \"python\", dict_a)))\n" 149 | ] 150 | }, 151 | { 152 | "cell_type": "code", 153 | "execution_count": 15, 154 | "metadata": {}, 155 | "outputs": [ 156 | { 157 | "name": "stdout", 158 | "output_type": "stream", 159 | "text": [ 160 | "[11, 22, 33]\n" 161 | ] 162 | } 163 | ], 164 | "source": [ 165 | "# Example 4\n", 166 | "\n", 167 | "list_a = [1, 2, 3]\n", 168 | "list_b = [10, 20, 30]\n", 169 | " \n", 170 | "print(list(map(lambda x, y: x + y, list_a, list_b)))" 171 | ] 172 | }, 173 | { 174 | "cell_type": "markdown", 175 | "metadata": {}, 176 | "source": [ 177 | "## Filter function\n", 178 | "\n", 179 | "Basic Syntax
\n", 180 | "```filter(function_object, iterable1, iterable2,...)```" 181 | ] 182 | }, 183 | { 184 | "cell_type": "code", 185 | "execution_count": 17, 186 | "metadata": {}, 187 | "outputs": [ 188 | { 189 | "data": { 190 | "text/plain": [ 191 | "" 192 | ] 193 | }, 194 | "execution_count": 17, 195 | "metadata": {}, 196 | "output_type": "execute_result" 197 | } 198 | ], 199 | "source": [ 200 | "# Example 1\n", 201 | "\n", 202 | "a = [1, 2, 3, 4, 5, 6]\n", 203 | "filter(lambda x : x % 2 == 0, a)" 204 | ] 205 | }, 206 | { 207 | "cell_type": "code", 208 | "execution_count": 18, 209 | "metadata": {}, 210 | "outputs": [ 211 | { 212 | "data": { 213 | "text/plain": [ 214 | "" 215 | ] 216 | }, 217 | "execution_count": 18, 218 | "metadata": {}, 219 | "output_type": "execute_result" 220 | } 221 | ], 222 | "source": [ 223 | "# Example 2\n", 224 | "\n", 225 | "dict_a = [{'name': 'python', 'points': 10}, {'name': 'java', 'points': 8}, {'name': 'python', 'points': 10}]\n", 226 | "\n", 227 | "filter(lambda x : x['name'] == 'python', dict_a)" 228 | ] 229 | }, 230 | { 231 | "cell_type": "markdown", 232 | "metadata": {}, 233 | "source": [ 234 | "## Comprehensions" 235 | ] 236 | }, 237 | { 238 | "cell_type": "markdown", 239 | "metadata": {}, 240 | "source": [ 241 | "#### Dictionary Comprehensions" 242 | ] 243 | }, 244 | { 245 | "cell_type": "code", 246 | "execution_count": 22, 247 | "metadata": {}, 248 | "outputs": [ 249 | { 250 | "name": "stdout", 251 | "output_type": "stream", 252 | "text": [ 253 | "{'milk': 0.7752, 'coffee': 1.9, 'bread': 1.9}\n" 254 | ] 255 | } 256 | ], 257 | "source": [ 258 | "# Example 1 \n", 259 | "\n", 260 | "old_price = {'milk': 1.02, 'coffee': 2.5, 'bread': 2.5}\n", 261 | "\n", 262 | "dollar_to_pound = 0.76\n", 263 | "new_price = {item: value*dollar_to_pound for (item, value) in old_price.items()}\n", 264 | "print(new_price)\n" 265 | ] 266 | }, 267 | { 268 | "cell_type": "code", 269 | "execution_count": 23, 270 | "metadata": {}, 271 | "outputs": [ 272 | { 273 | "name": "stdout", 274 | "output_type": "stream", 275 | "text": [ 276 | "{'john': 33}\n" 277 | ] 278 | } 279 | ], 280 | "source": [ 281 | "# Example 2 - with if condition\n", 282 | "\n", 283 | "original_dict = {'jack': 38, 'michael': 48, 'guido': 57, 'john': 33}\n", 284 | "\n", 285 | "new_dict = {k: v for (k, v) in original_dict.items() if v % 2 != 0 if v < 40}\n", 286 | "print(new_dict)" 287 | ] 288 | }, 289 | { 290 | "cell_type": "code", 291 | "execution_count": 24, 292 | "metadata": {}, 293 | "outputs": [ 294 | { 295 | "name": "stdout", 296 | "output_type": "stream", 297 | "text": [ 298 | "{'jack': 'young', 'michael': 'old', 'guido': 'old', 'john': 'young'}\n" 299 | ] 300 | } 301 | ], 302 | "source": [ 303 | "# Example 3 - with if else\n", 304 | "\n", 305 | "original_dict = {'jack': 38, 'michael': 48, 'guido': 57, 'john': 33}\n", 306 | "\n", 307 | "new_dict_1 = {k: ('old' if v > 40 else 'young')\n", 308 | " for (k, v) in original_dict.items()}\n", 309 | "print(new_dict_1)" 310 | ] 311 | }, 312 | { 313 | "cell_type": "code", 314 | "execution_count": 25, 315 | "metadata": {}, 316 | "outputs": [ 317 | { 318 | "name": "stdout", 319 | "output_type": "stream", 320 | "text": [ 321 | "{2: {1: 2, 2: 4, 3: 6, 4: 8, 5: 10}, 3: {1: 3, 2: 6, 3: 9, 4: 12, 5: 15}, 4: {1: 4, 2: 8, 3: 12, 4: 16, 5: 20}}\n" 322 | ] 323 | } 324 | ], 325 | "source": [ 326 | "# Example 4 - nested dictionary comprehensions\n", 327 | "\n", 328 | "dictionary = {\n", 329 | " k1: {k2: k1 * k2 for k2 in range(1, 6)} for k1 in range(2, 5)\n", 330 | "}\n", 331 | "print(dictionary)" 332 | ] 333 | }, 334 | { 335 | "cell_type": "markdown", 336 | "metadata": {}, 337 | "source": [ 338 | "#### Set Comprehensions" 339 | ] 340 | }, 341 | { 342 | "cell_type": "code", 343 | "execution_count": 29, 344 | "metadata": { 345 | "scrolled": true 346 | }, 347 | "outputs": [ 348 | { 349 | "data": { 350 | "text/plain": [ 351 | "{'Alice', 'Arnold', 'Bill', 'Mary'}" 352 | ] 353 | }, 354 | "execution_count": 29, 355 | "metadata": {}, 356 | "output_type": "execute_result" 357 | } 358 | ], 359 | "source": [ 360 | "# Example\n", 361 | "\n", 362 | "names = [ 'Arnold', 'BILL', 'alice', 'arnold', 'MARY', 'J', 'BIll' ,'maRy']\n", 363 | "res = {name.capitalize() for name in names if len(name) > 1}\n", 364 | "res" 365 | ] 366 | }, 367 | { 368 | "cell_type": "markdown", 369 | "metadata": {}, 370 | "source": [ 371 | "## Global, Local and Nonlocal" 372 | ] 373 | }, 374 | { 375 | "attachments": {}, 376 | "cell_type": "markdown", 377 | "metadata": {}, 378 | "source": [ 379 | "### Variable Scoping\n", 380 | "\n", 381 | "" 382 | ] 383 | }, 384 | { 385 | "cell_type": "markdown", 386 | "metadata": {}, 387 | "source": [ 388 | "Global Variables
\n", 389 | "In Python, a variable declared outside of the function or in global scope is known as a global variable. This means that a global variable can be accessed inside or outside of the function." 390 | ] 391 | }, 392 | { 393 | "cell_type": "code", 394 | "execution_count": 6, 395 | "metadata": {}, 396 | "outputs": [ 397 | { 398 | "name": "stdout", 399 | "output_type": "stream", 400 | "text": [ 401 | "x inside: global\n", 402 | "x outside: global\n" 403 | ] 404 | } 405 | ], 406 | "source": [ 407 | "# example 1\n", 408 | "\n", 409 | "x = \"global\"\n", 410 | "\n", 411 | "def foo():\n", 412 | " print(\"x inside:\", x)\n", 413 | "\n", 414 | "\n", 415 | "foo()\n", 416 | "print(\"x outside:\", x)" 417 | ] 418 | }, 419 | { 420 | "cell_type": "code", 421 | "execution_count": 12, 422 | "metadata": {}, 423 | "outputs": [ 424 | { 425 | "name": "stdout", 426 | "output_type": "stream", 427 | "text": [ 428 | "10\n" 429 | ] 430 | } 431 | ], 432 | "source": [ 433 | "# Example 2\n", 434 | "\n", 435 | "x = 5\n", 436 | "\n", 437 | "def foo():\n", 438 | " x = 5\n", 439 | " x = x * 2\n", 440 | " print(x)\n", 441 | "\n", 442 | "foo()" 443 | ] 444 | }, 445 | { 446 | "cell_type": "code", 447 | "execution_count": 13, 448 | "metadata": {}, 449 | "outputs": [ 450 | { 451 | "name": "stdout", 452 | "output_type": "stream", 453 | "text": [ 454 | "10\n", 455 | "11\n", 456 | "11\n" 457 | ] 458 | } 459 | ], 460 | "source": [ 461 | "# Example 3\n", 462 | "\n", 463 | "x = 10\n", 464 | "def foobar():\n", 465 | " global x\n", 466 | " print(x)\n", 467 | " x += 1\n", 468 | " print(x)\n", 469 | "\n", 470 | "foobar()\n", 471 | "print(x)" 472 | ] 473 | }, 474 | { 475 | "cell_type": "markdown", 476 | "metadata": {}, 477 | "source": [ 478 | "Rules of global Keyword
\n", 479 | "The basic rules for global keyword in Python are:
\n", 480 | "\n", 481 | "- When we create a variable inside a function, it is local by default.
\n", 482 | "- When we define a variable outside of a function, it is global by default. You don't have to use global keyword.
\n", 483 | "- We use global keyword to read and write a global variable inside a function.
\n", 484 | "- Use of global keyword outside a function has no effect.
" 485 | ] 486 | }, 487 | { 488 | "cell_type": "code", 489 | "execution_count": 19, 490 | "metadata": {}, 491 | "outputs": [ 492 | { 493 | "name": "stdout", 494 | "output_type": "stream", 495 | "text": [ 496 | "Before calling bar: 20\n", 497 | "Calling bar now\n" 498 | ] 499 | }, 500 | { 501 | "ename": "NameError", 502 | "evalue": "name 'd' is not defined", 503 | "output_type": "error", 504 | "traceback": [ 505 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 506 | "\u001b[1;31mNameError\u001b[0m Traceback (most recent call last)", 507 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[0;32m 14\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"After calling bar: \"\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0md\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 15\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 16\u001b[1;33m \u001b[0mfoo\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 17\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 18\u001b[0m \u001b[1;31m# print(\"x in main: \", d)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n", 508 | "\u001b[1;32m\u001b[0m in \u001b[0;36mfoo\u001b[1;34m()\u001b[0m\n\u001b[0;32m 11\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Before calling bar: \"\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0md\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 12\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"Calling bar now\"\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m---> 13\u001b[1;33m \u001b[0mbar\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 14\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;34m\"After calling bar: \"\u001b[0m\u001b[1;33m,\u001b[0m \u001b[0md\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 15\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n", 509 | "\u001b[1;32m\u001b[0m in \u001b[0;36mbar\u001b[1;34m()\u001b[0m\n\u001b[0;32m 6\u001b[0m \u001b[1;32mdef\u001b[0m \u001b[0mbar\u001b[0m\u001b[1;33m(\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m:\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 7\u001b[0m \u001b[1;32mglobal\u001b[0m \u001b[0md\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[1;32m----> 8\u001b[1;33m \u001b[0md\u001b[0m \u001b[1;33m+=\u001b[0m\u001b[1;36m1\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 9\u001b[0m \u001b[0mprint\u001b[0m\u001b[1;33m(\u001b[0m\u001b[0md\u001b[0m\u001b[1;33m)\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 10\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n", 510 | "\u001b[1;31mNameError\u001b[0m: name 'd' is not defined" 511 | ] 512 | } 513 | ], 514 | "source": [ 515 | "# global keyword in nested functions\n", 516 | "\n", 517 | "def foo():\n", 518 | " d = 20\n", 519 | "\n", 520 | " def bar():\n", 521 | " global d\n", 522 | " d +=1\n", 523 | " print(d)\n", 524 | " \n", 525 | " print(\"Before calling bar: \", d)\n", 526 | " print(\"Calling bar now\")\n", 527 | " bar()\n", 528 | " print(\"After calling bar: \", d)\n", 529 | "\n", 530 | "foo()\n", 531 | "\n", 532 | "# print(\"x in main: \", d)" 533 | ] 534 | }, 535 | { 536 | "cell_type": "markdown", 537 | "metadata": {}, 538 | "source": [ 539 | "## Understanding nonlocal variable\n", 540 | "\n", 541 | "Nonlocal variables are used in nested functions whose local scope is not defined. This means that the variable can be neither in the local nor the global scope." 542 | ] 543 | }, 544 | { 545 | "cell_type": "code", 546 | "execution_count": 1, 547 | "metadata": {}, 548 | "outputs": [ 549 | { 550 | "name": "stdout", 551 | "output_type": "stream", 552 | "text": [ 553 | "Some value + Something else\n", 554 | "Some local value + Something else\n" 555 | ] 556 | } 557 | ], 558 | "source": [ 559 | "gv = \"Some value\" # global variable\n", 560 | "\n", 561 | "def func():\n", 562 | " lv = \"Some local value\" # local variable\n", 563 | " def nested_func():\n", 564 | " global gv\n", 565 | " gv += \" + Something else\"\n", 566 | " print(gv)\n", 567 | " nonlocal lv\n", 568 | " lv += \" + Something else\"\n", 569 | " print(lv)\n", 570 | " nested_func()\n", 571 | " \n", 572 | "func()" 573 | ] 574 | }, 575 | { 576 | "cell_type": "code", 577 | "execution_count": 20, 578 | "metadata": {}, 579 | "outputs": [ 580 | { 581 | "ename": "SyntaxError", 582 | "evalue": "no binding for nonlocal 'gv' found (, line 8)", 583 | "output_type": "error", 584 | "traceback": [ 585 | "\u001b[1;36m File \u001b[1;32m\"\"\u001b[1;36m, line \u001b[1;32m8\u001b[0m\n\u001b[1;33m nonlocal gv\u001b[0m\n\u001b[1;37m ^\u001b[0m\n\u001b[1;31mSyntaxError\u001b[0m\u001b[1;31m:\u001b[0m no binding for nonlocal 'gv' found\n" 586 | ] 587 | } 588 | ], 589 | "source": [ 590 | "# Using nonlocal we can't change global scope variables\n", 591 | "\n", 592 | "gv = \"Some value\" # global variable\n", 593 | "\n", 594 | "def func():\n", 595 | " lv = \"Some local value\" # local variable\n", 596 | " def nested_func():\n", 597 | " nonlocal gv\n", 598 | " gv += \" + Something else\"\n", 599 | " print(gv)\n", 600 | " nonlocal lv\n", 601 | " lv += \" + Something else\"\n", 602 | " print(lv)\n", 603 | " nested_func()\n", 604 | " \n", 605 | "func()" 606 | ] 607 | }, 608 | { 609 | "cell_type": "markdown", 610 | "metadata": {}, 611 | "source": [ 612 | "### Automation Ideas using Python\n", 613 | "\n", 614 | "- Write a CLI to check COVID-19 cases on terminal\n", 615 | "- Write a CLI to check weather details on terminal\n", 616 | "- Automate the clutter in your Download/Desktop folder\n", 617 | "- Write a Script to keep your mouse moving (#WFH hack :D)\n", 618 | "- Write a watcher script to check for item with less price [to be picked later]" 619 | ] 620 | }, 621 | { 622 | "cell_type": "code", 623 | "execution_count": null, 624 | "metadata": {}, 625 | "outputs": [], 626 | "source": [] 627 | } 628 | ], 629 | "metadata": { 630 | "kernelspec": { 631 | "display_name": "Python 3", 632 | "language": "python", 633 | "name": "python3" 634 | }, 635 | "language_info": { 636 | "codemirror_mode": { 637 | "name": "ipython", 638 | "version": 3 639 | }, 640 | "file_extension": ".py", 641 | "mimetype": "text/x-python", 642 | "name": "python", 643 | "nbconvert_exporter": "python", 644 | "pygments_lexer": "ipython3", 645 | "version": "3.7.5" 646 | } 647 | }, 648 | "nbformat": 4, 649 | "nbformat_minor": 2 650 | } 651 | -------------------------------------------------------------------------------- /notebooks/6_imports_module_packages.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "### Understanding \\__name\\__ built in\n", 8 | "\n", 9 | "The \\__name\\__ is a special built-in variable which evaluates to the name of the current module. However, if a module is being run directly (from command line), then \\__name\\__ instead is set to the string “\\__main\\__”." 10 | ] 11 | }, 12 | { 13 | "cell_type": "code", 14 | "execution_count": 8, 15 | "metadata": { 16 | "scrolled": true 17 | }, 18 | "outputs": [ 19 | { 20 | "name": "stdout", 21 | "output_type": "stream", 22 | "text": [ 23 | "foo.__name__ set to __main__\n" 24 | ] 25 | } 26 | ], 27 | "source": [ 28 | "# foo.py\n", 29 | "import bar\n", 30 | "\n", 31 | "print(\"foo.__name__ set to \", __name__)" 32 | ] 33 | }, 34 | { 35 | "cell_type": "code", 36 | "execution_count": 9, 37 | "metadata": {}, 38 | "outputs": [ 39 | { 40 | "name": "stdout", 41 | "output_type": "stream", 42 | "text": [ 43 | "bar.__name__ set to __main__\n" 44 | ] 45 | } 46 | ], 47 | "source": [ 48 | "# bar.py\n", 49 | "\n", 50 | "print(\"bar.__name__ set to \", __name__)" 51 | ] 52 | }, 53 | { 54 | "cell_type": "markdown", 55 | "metadata": {}, 56 | "source": [ 57 | "### Use of \\__name\\__ == \"\\__main__\\\"" 58 | ] 59 | }, 60 | { 61 | "cell_type": "markdown", 62 | "metadata": {}, 63 | "source": [ 64 | "Using \\__name\\__ == \"\\__main\\__\" we can find out whether the value of \"\\__name\\__\" built in is equals to \"\\__main\\__\" or not. If it is equivalent it means module is directly being called form the terminal itself. If not then means it is being called form some other module." 65 | ] 66 | }, 67 | { 68 | "cell_type": "code", 69 | "execution_count": null, 70 | "metadata": {}, 71 | "outputs": [], 72 | "source": [ 73 | "# let's look at some of the examples" 74 | ] 75 | }, 76 | { 77 | "cell_type": "code", 78 | "execution_count": 10, 79 | "metadata": {}, 80 | "outputs": [ 81 | { 82 | "name": "stdout", 83 | "output_type": "stream", 84 | "text": [ 85 | "top-level in person module\n", 86 | "person mod is run directly\n" 87 | ] 88 | } 89 | ], 90 | "source": [ 91 | "v edf" 92 | ] 93 | }, 94 | { 95 | "cell_type": "code", 96 | "execution_count": null, 97 | "metadata": {}, 98 | "outputs": [], 99 | "source": [ 100 | "# module utils.py\n", 101 | "import person\n", 102 | "\n", 103 | "person.creds()\n", 104 | "\n", 105 | "if __name__ == \"__main__\":\n", 106 | " print(\"utils mod is run directly\")\n", 107 | "else:\n", 108 | " print(\"utils mod is imported into another module\")" 109 | ] 110 | }, 111 | { 112 | "cell_type": "markdown", 113 | "metadata": {}, 114 | "source": [ 115 | "### Modules and Packages" 116 | ] 117 | }, 118 | { 119 | "cell_type": "markdown", 120 | "metadata": {}, 121 | "source": [ 122 | "Python modules and Python packages, two mechanisms that facilitate modular programming." 123 | ] 124 | }, 125 | { 126 | "cell_type": "markdown", 127 | "metadata": {}, 128 | "source": [ 129 | "#### Modular Programming\n", 130 | "\n", 131 | "It refers to the process of breaking a large, unwieldy programming task into separate, smaller, more manageable subtasks or modules. Advantages are below - \n", 132 | "\n", 133 | "- Simplicity\n", 134 | "- Maintainability\n", 135 | "- Reusability\n", 136 | "- Scoping" 137 | ] 138 | }, 139 | { 140 | "cell_type": "markdown", 141 | "metadata": {}, 142 | "source": [ 143 | "#### What are modules in Python?\n", 144 | "\n", 145 | "Modules refer to a file containing Python statements and definitions.\n", 146 | "\n", 147 | "A file containing Python code, for example: example.py, is called a module, and its module name would be example." 148 | ] 149 | }, 150 | { 151 | "cell_type": "code", 152 | "execution_count": 16, 153 | "metadata": {}, 154 | "outputs": [], 155 | "source": [ 156 | "# example.py\n", 157 | "# Python Module example\n", 158 | "\n", 159 | "def add(a, b):\n", 160 | " \"\"\"This program adds two\n", 161 | " numbers and return the result\"\"\"\n", 162 | "\n", 163 | " result = a + b\n", 164 | " return result" 165 | ] 166 | }, 167 | { 168 | "cell_type": "code", 169 | "execution_count": 19, 170 | "metadata": {}, 171 | "outputs": [], 172 | "source": [ 173 | "# let's try and import this in Python terminal\n", 174 | "# call function add()" 175 | ] 176 | }, 177 | { 178 | "cell_type": "code", 179 | "execution_count": 20, 180 | "metadata": {}, 181 | "outputs": [ 182 | { 183 | "name": "stdout", 184 | "output_type": "stream", 185 | "text": [ 186 | "The value of pi is 3.141592653589793\n" 187 | ] 188 | } 189 | ], 190 | "source": [ 191 | "# import some native libraies\n", 192 | "# standard module math\n", 193 | "\n", 194 | "import math\n", 195 | "print(\"The value of pi is\", math.pi)" 196 | ] 197 | }, 198 | { 199 | "cell_type": "markdown", 200 | "metadata": {}, 201 | "source": [ 202 | "#### The Module Search Path" 203 | ] 204 | }, 205 | { 206 | "cell_type": "code", 207 | "execution_count": null, 208 | "metadata": {}, 209 | "outputs": [], 210 | "source": [ 211 | "import example" 212 | ] 213 | }, 214 | { 215 | "cell_type": "markdown", 216 | "metadata": {}, 217 | "source": [ 218 | "When the interpreter executes the above import statement, it searches for example.py in a list of directories assembled from the following sources:\n", 219 | "\n", 220 | "- The directory from which the input script was run or the current directory\n", 221 | "- The list of directories contained in the PYTHONPATH environment variable, if it is set.\n", 222 | "- An installation-dependent list of directories configured at the time Python is installed\n", 223 | "\n", 224 | "The resulting search path is accessible in the Python variable sys.path, which is obtained from a module named sys:" 225 | ] 226 | }, 227 | { 228 | "cell_type": "code", 229 | "execution_count": 25, 230 | "metadata": {}, 231 | "outputs": [ 232 | { 233 | "name": "stdout", 234 | "output_type": "stream", 235 | "text": [ 236 | "C:\\cygwin64\\home\\Sanchit_Balchandani\\Workspace\\python-ws\\python-for-devops\\notebooks\n", 237 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\python37.zip\n", 238 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\DLLs\n", 239 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\lib\n", 240 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\n", 241 | "\n", 242 | "C:\\Users\\Sanchit_Balchandani\\AppData\\Roaming\\Python\\Python37\\site-packages\n", 243 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\lib\\site-packages\n", 244 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\lib\\site-packages\\win32\n", 245 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\lib\\site-packages\\win32\\lib\n", 246 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\lib\\site-packages\\Pythonwin\n", 247 | "c:\\users\\sanchit_balchandani\\appdata\\local\\programs\\python\\python37\\lib\\site-packages\\IPython\\extensions\n", 248 | "C:\\cygwin64\\home\\Sanchit_Balchandani\\.ipython\n" 249 | ] 250 | } 251 | ], 252 | "source": [ 253 | "import sys\n", 254 | "for i in sys.path: print(i)" 255 | ] 256 | }, 257 | { 258 | "cell_type": "code", 259 | "execution_count": 28, 260 | "metadata": {}, 261 | "outputs": [ 262 | { 263 | "data": { 264 | "text/plain": [ 265 | "'c:\\\\users\\\\sanchit_balchandani\\\\appdata\\\\local\\\\programs\\\\python\\\\python37\\\\lib\\\\site-packages\\\\requests\\\\__init__.py'" 266 | ] 267 | }, 268 | "execution_count": 28, 269 | "metadata": {}, 270 | "output_type": "execute_result" 271 | } 272 | ], 273 | "source": [ 274 | "import requests\n", 275 | "\n", 276 | "requests.__file__" 277 | ] 278 | }, 279 | { 280 | "cell_type": "code", 281 | "execution_count": 35, 282 | "metadata": {}, 283 | "outputs": [ 284 | { 285 | "name": "stdout", 286 | "output_type": "stream", 287 | "text": [ 288 | "C:\\cygwin64\\home\\Sanchit_Balchandani\\Workspace\\python-ws\\python-for-devops\\notebooks\\modules_and_packages\\math.py\n" 289 | ] 290 | }, 291 | { 292 | "data": { 293 | "text/plain": [ 294 | "1234" 295 | ] 296 | }, 297 | "execution_count": 35, 298 | "metadata": {}, 299 | "output_type": "execute_result" 300 | } 301 | ], 302 | "source": [ 303 | "# using from keyword to import \n", 304 | "\n", 305 | "import math\n", 306 | "from modules_and_packages import math\n", 307 | "\n", 308 | "print(math.__file__)\n", 309 | "\n", 310 | "math.pi" 311 | ] 312 | }, 313 | { 314 | "cell_type": "code", 315 | "execution_count": 39, 316 | "metadata": {}, 317 | "outputs": [], 318 | "source": [ 319 | "# Use of as keyword (renaming module)\n", 320 | "\n", 321 | "# let look an example on terminal\n", 322 | "\n", 323 | "# rom import as \n", 324 | "\n", 325 | "# import as " 326 | ] 327 | }, 328 | { 329 | "cell_type": "code", 330 | "execution_count": 40, 331 | "metadata": {}, 332 | "outputs": [ 333 | { 334 | "name": "stdout", 335 | "output_type": "stream", 336 | "text": [ 337 | "Module not found\n" 338 | ] 339 | } 340 | ], 341 | "source": [ 342 | "# Use of try and except for import validations\n", 343 | "\n", 344 | "try:\n", 345 | " # Non-existent module\n", 346 | " import baz\n", 347 | "except ImportError:\n", 348 | " print('Module not found')\n" 349 | ] 350 | }, 351 | { 352 | "cell_type": "markdown", 353 | "metadata": {}, 354 | "source": [ 355 | "#### The dir() Function\n", 356 | "The built-in function dir() returns a list of defined names in a namespace. Without arguments, it produces an alphabetically sorted list of names in the current local symbol table:\n", 357 | "\n" 358 | ] 359 | }, 360 | { 361 | "cell_type": "code", 362 | "execution_count": 41, 363 | "metadata": { 364 | "scrolled": true 365 | }, 366 | "outputs": [ 367 | { 368 | "data": { 369 | "text/plain": [ 370 | "['In',\n", 371 | " 'Out',\n", 372 | " '_',\n", 373 | " '_23',\n", 374 | " '_27',\n", 375 | " '_28',\n", 376 | " '_29',\n", 377 | " '_30',\n", 378 | " '_31',\n", 379 | " '_32',\n", 380 | " '_34',\n", 381 | " '_35',\n", 382 | " '__',\n", 383 | " '___',\n", 384 | " '__builtin__',\n", 385 | " '__builtins__',\n", 386 | " '__doc__',\n", 387 | " '__loader__',\n", 388 | " '__name__',\n", 389 | " '__package__',\n", 390 | " '__spec__',\n", 391 | " '_dh',\n", 392 | " '_i',\n", 393 | " '_i1',\n", 394 | " '_i10',\n", 395 | " '_i11',\n", 396 | " '_i12',\n", 397 | " '_i13',\n", 398 | " '_i14',\n", 399 | " '_i15',\n", 400 | " '_i16',\n", 401 | " '_i17',\n", 402 | " '_i18',\n", 403 | " '_i19',\n", 404 | " '_i2',\n", 405 | " '_i20',\n", 406 | " '_i21',\n", 407 | " '_i22',\n", 408 | " '_i23',\n", 409 | " '_i24',\n", 410 | " '_i25',\n", 411 | " '_i26',\n", 412 | " '_i27',\n", 413 | " '_i28',\n", 414 | " '_i29',\n", 415 | " '_i3',\n", 416 | " '_i30',\n", 417 | " '_i31',\n", 418 | " '_i32',\n", 419 | " '_i33',\n", 420 | " '_i34',\n", 421 | " '_i35',\n", 422 | " '_i36',\n", 423 | " '_i37',\n", 424 | " '_i38',\n", 425 | " '_i39',\n", 426 | " '_i4',\n", 427 | " '_i40',\n", 428 | " '_i41',\n", 429 | " '_i5',\n", 430 | " '_i6',\n", 431 | " '_i7',\n", 432 | " '_i8',\n", 433 | " '_i9',\n", 434 | " '_ih',\n", 435 | " '_ii',\n", 436 | " '_iii',\n", 437 | " '_oh',\n", 438 | " 'add',\n", 439 | " 'creds',\n", 440 | " 'exit',\n", 441 | " 'get_ipython',\n", 442 | " 'i',\n", 443 | " 'math',\n", 444 | " 'proj',\n", 445 | " 'quit',\n", 446 | " 'requests',\n", 447 | " 'sys']" 448 | ] 449 | }, 450 | "execution_count": 41, 451 | "metadata": {}, 452 | "output_type": "execute_result" 453 | } 454 | ], 455 | "source": [ 456 | "dir()" 457 | ] 458 | }, 459 | { 460 | "cell_type": "code", 461 | "execution_count": 42, 462 | "metadata": {}, 463 | "outputs": [], 464 | "source": [ 465 | "my_funny_randon_horrible_variable = [\"Sanchit\"]" 466 | ] 467 | }, 468 | { 469 | "cell_type": "code", 470 | "execution_count": 43, 471 | "metadata": { 472 | "scrolled": true 473 | }, 474 | "outputs": [ 475 | { 476 | "data": { 477 | "text/plain": [ 478 | "['In',\n", 479 | " 'Out',\n", 480 | " '_',\n", 481 | " '_23',\n", 482 | " '_27',\n", 483 | " '_28',\n", 484 | " '_29',\n", 485 | " '_30',\n", 486 | " '_31',\n", 487 | " '_32',\n", 488 | " '_34',\n", 489 | " '_35',\n", 490 | " '_41',\n", 491 | " '__',\n", 492 | " '___',\n", 493 | " '__builtin__',\n", 494 | " '__builtins__',\n", 495 | " '__doc__',\n", 496 | " '__loader__',\n", 497 | " '__name__',\n", 498 | " '__package__',\n", 499 | " '__spec__',\n", 500 | " '_dh',\n", 501 | " '_i',\n", 502 | " '_i1',\n", 503 | " '_i10',\n", 504 | " '_i11',\n", 505 | " '_i12',\n", 506 | " '_i13',\n", 507 | " '_i14',\n", 508 | " '_i15',\n", 509 | " '_i16',\n", 510 | " '_i17',\n", 511 | " '_i18',\n", 512 | " '_i19',\n", 513 | " '_i2',\n", 514 | " '_i20',\n", 515 | " '_i21',\n", 516 | " '_i22',\n", 517 | " '_i23',\n", 518 | " '_i24',\n", 519 | " '_i25',\n", 520 | " '_i26',\n", 521 | " '_i27',\n", 522 | " '_i28',\n", 523 | " '_i29',\n", 524 | " '_i3',\n", 525 | " '_i30',\n", 526 | " '_i31',\n", 527 | " '_i32',\n", 528 | " '_i33',\n", 529 | " '_i34',\n", 530 | " '_i35',\n", 531 | " '_i36',\n", 532 | " '_i37',\n", 533 | " '_i38',\n", 534 | " '_i39',\n", 535 | " '_i4',\n", 536 | " '_i40',\n", 537 | " '_i41',\n", 538 | " '_i42',\n", 539 | " '_i43',\n", 540 | " '_i5',\n", 541 | " '_i6',\n", 542 | " '_i7',\n", 543 | " '_i8',\n", 544 | " '_i9',\n", 545 | " '_ih',\n", 546 | " '_ii',\n", 547 | " '_iii',\n", 548 | " '_oh',\n", 549 | " 'add',\n", 550 | " 'creds',\n", 551 | " 'exit',\n", 552 | " 'get_ipython',\n", 553 | " 'i',\n", 554 | " 'math',\n", 555 | " 'my_funny_randon_horrible_variable',\n", 556 | " 'proj',\n", 557 | " 'quit',\n", 558 | " 'requests',\n", 559 | " 'sys']" 560 | ] 561 | }, 562 | "execution_count": 43, 563 | "metadata": {}, 564 | "output_type": "execute_result" 565 | } 566 | ], 567 | "source": [ 568 | "dir()" 569 | ] 570 | }, 571 | { 572 | "cell_type": "markdown", 573 | "metadata": {}, 574 | "source": [ 575 | "#### Reloading a Module" 576 | ] 577 | }, 578 | { 579 | "cell_type": "markdown", 580 | "metadata": {}, 581 | "source": [ 582 | "For reasons of efficiency, a module is only loaded once per interpreter session. That is fine for function and class definitions, which typically make up the bulk of a module’s contents. But a module can contain executable statements as well, usually for initialization. Be aware that these statements will only be executed the first time a module is imported." 583 | ] 584 | }, 585 | { 586 | "cell_type": "code", 587 | "execution_count": 47, 588 | "metadata": {}, 589 | "outputs": [], 590 | "source": [ 591 | "# Let's try some examples on Terminal" 592 | ] 593 | }, 594 | { 595 | "cell_type": "code", 596 | "execution_count": 48, 597 | "metadata": {}, 598 | "outputs": [ 599 | { 600 | "ename": "ModuleNotFoundError", 601 | "evalue": "No module named 'mod'", 602 | "output_type": "error", 603 | "traceback": [ 604 | "\u001b[1;31m---------------------------------------------------------------------------\u001b[0m", 605 | "\u001b[1;31mModuleNotFoundError\u001b[0m Traceback (most recent call last)", 606 | "\u001b[1;32m\u001b[0m in \u001b[0;36m\u001b[1;34m\u001b[0m\n\u001b[1;32m----> 1\u001b[1;33m \u001b[1;32mimport\u001b[0m \u001b[0mmod\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0m\u001b[0;32m 2\u001b[0m \u001b[0ma\u001b[0m \u001b[1;33m=\u001b[0m \u001b[1;33m[\u001b[0m\u001b[1;36m100\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m200\u001b[0m\u001b[1;33m,\u001b[0m \u001b[1;36m300\u001b[0m\u001b[1;33m]\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 3\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 4\u001b[0m \u001b[1;32mimport\u001b[0m \u001b[0mmod\u001b[0m\u001b[1;33m\u001b[0m\u001b[1;33m\u001b[0m\u001b[0m\n\u001b[0;32m 5\u001b[0m \u001b[1;33m\u001b[0m\u001b[0m\n", 607 | "\u001b[1;31mModuleNotFoundError\u001b[0m: No module named 'mod'" 608 | ] 609 | } 610 | ], 611 | "source": [ 612 | "# Sample Example, will not work here\n", 613 | "\n", 614 | "import mod\n", 615 | "a = [100, 200, 300]\n", 616 | "\n", 617 | "import mod\n", 618 | "\n", 619 | "import importlib\n", 620 | "importlib.reload(mod)" 621 | ] 622 | }, 623 | { 624 | "cell_type": "markdown", 625 | "metadata": {}, 626 | "source": [ 627 | "#### What are packages?" 628 | ] 629 | }, 630 | { 631 | "cell_type": "markdown", 632 | "metadata": {}, 633 | "source": [ 634 | "Package Initialization\n", 635 | "If a file named \\__init\\__.py is present in a package directory, it is invoked when the package or a module in the package is imported. This can be used for execution of package initialization code, such as initialization of package-level data.\n", 636 | "\n", 637 | "For example, consider the following \\__init\\__.py file:" 638 | ] 639 | }, 640 | { 641 | "attachments": {}, 642 | "cell_type": "markdown", 643 | "metadata": {}, 644 | "source": [ 645 | "" 646 | ] 647 | }, 648 | { 649 | "cell_type": "code", 650 | "execution_count": null, 651 | "metadata": {}, 652 | "outputs": [], 653 | "source": [ 654 | "# Let's try some examples on terminal" 655 | ] 656 | }, 657 | { 658 | "attachments": {}, 659 | "cell_type": "markdown", 660 | "metadata": {}, 661 | "source": [ 662 | "#### Subpackages\n", 663 | "\n", 664 | "" 665 | ] 666 | }, 667 | { 668 | "cell_type": "markdown", 669 | "metadata": {}, 670 | "source": [ 671 | "#### Absolute Import\n", 672 | "In this type of import, we specify the full path of the package/module/function to be imported. A dot(.) is used in pace of slash(/) for the directory structure.\n", 673 | "\n", 674 | "Consider the following directory structure for a package.\n", 675 | "\n", 676 | "python_project_name/packageA/moduleA1.py\n", 677 | "python_project_name/packageA/moduleA2.py" 678 | ] 679 | }, 680 | { 681 | "cell_type": "code", 682 | "execution_count": 50, 683 | "metadata": {}, 684 | "outputs": [], 685 | "source": [ 686 | "# from packageA.moduleA2 import myfunc" 687 | ] 688 | }, 689 | { 690 | "cell_type": "markdown", 691 | "metadata": {}, 692 | "source": [ 693 | "#### Relative Import\n", 694 | "In relative import, we mention the path of the imported package as relative to the location of the current script which is using the imported module.\n", 695 | "\n", 696 | "A dot indicates one directory up from the current location and two dots indicates two directories up and so on.\n", 697 | "\n", 698 | "Consider the following directory structure for a package.\n", 699 | "\n", 700 | "python_project_name/packageA/moduleA1.py \n", 701 | "\n", 702 | "\n", 703 | "python_project_name/packageB/moduleB1.py" 704 | ] 705 | }, 706 | { 707 | "cell_type": "code", 708 | "execution_count": null, 709 | "metadata": {}, 710 | "outputs": [], 711 | "source": [ 712 | "from ..packageA import moduleA1" 713 | ] 714 | } 715 | ], 716 | "metadata": { 717 | "kernelspec": { 718 | "display_name": "Python 3", 719 | "language": "python", 720 | "name": "python3" 721 | }, 722 | "language_info": { 723 | "codemirror_mode": { 724 | "name": "ipython", 725 | "version": 3 726 | }, 727 | "file_extension": ".py", 728 | "mimetype": "text/x-python", 729 | "name": "python", 730 | "nbconvert_exporter": "python", 731 | "pygments_lexer": "ipython3", 732 | "version": "3.7.5" 733 | } 734 | }, 735 | "nbformat": 4, 736 | "nbformat_minor": 2 737 | } 738 | -------------------------------------------------------------------------------- /notebooks/7_decorators_generators_iterators.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# Decorators\n", 8 | "\n", 9 | "Before discussing about decorators, In previous session Sanchit explained about functions and how to pass arguments to a function and how to return a value from a function.\n", 10 | "\n", 11 | "In python we can pass function as a parameter to a function." 12 | ] 13 | }, 14 | { 15 | "cell_type": "code", 16 | "execution_count": 1, 17 | "metadata": {}, 18 | "outputs": [ 19 | { 20 | "name": "stdout", 21 | "output_type": "stream", 22 | "text": [ 23 | "5\n", 24 | "3\n" 25 | ] 26 | } 27 | ], 28 | "source": [ 29 | "def inc(x):\n", 30 | " print(x+1)\n", 31 | " \n", 32 | "def dec(x):\n", 33 | " print(x-1)\n", 34 | " \n", 35 | "def gen(fun, x):\n", 36 | " fun(x)\n", 37 | " \n", 38 | "gen(inc, 4)\n", 39 | "gen(dec, 4)" 40 | ] 41 | }, 42 | { 43 | "cell_type": "markdown", 44 | "metadata": {}, 45 | "source": [ 46 | "We can also return a function from another function" 47 | ] 48 | }, 49 | { 50 | "cell_type": "code", 51 | "execution_count": 3, 52 | "metadata": {}, 53 | "outputs": [ 54 | { 55 | "name": "stdout", 56 | "output_type": "stream", 57 | "text": [ 58 | "call func\n", 59 | "this is return function\n" 60 | ] 61 | } 62 | ], 63 | "source": [ 64 | "def ret_func():\n", 65 | " print ('this is return function')\n", 66 | " \n", 67 | "def call_func():\n", 68 | " print('call func')\n", 69 | " return ret_func\n", 70 | "\n", 71 | "x = call_func()\n", 72 | "x()" 73 | ] 74 | }, 75 | { 76 | "cell_type": "markdown", 77 | "metadata": {}, 78 | "source": [ 79 | "Python also supports nested functions we can define a function inside another function" 80 | ] 81 | }, 82 | { 83 | "cell_type": "code", 84 | "execution_count": 4, 85 | "metadata": {}, 86 | "outputs": [ 87 | { 88 | "name": "stdout", 89 | "output_type": "stream", 90 | "text": [ 91 | "outer\n", 92 | "inner\n" 93 | ] 94 | } 95 | ], 96 | "source": [ 97 | "def outer():\n", 98 | " print ('outer')\n", 99 | " def inner():\n", 100 | " print ('inner')\n", 101 | " return inner\n", 102 | "\n", 103 | "x = outer()\n", 104 | "x()" 105 | ] 106 | }, 107 | { 108 | "cell_type": "markdown", 109 | "metadata": {}, 110 | "source": [ 111 | "Now lets come back to our topic here i.e decorators, basically a decorator takes in a function, adds some functionality and returns it." 112 | ] 113 | }, 114 | { 115 | "cell_type": "code", 116 | "execution_count": 5, 117 | "metadata": {}, 118 | "outputs": [ 119 | { 120 | "name": "stdout", 121 | "output_type": "stream", 122 | "text": [ 123 | "Hi\n", 124 | "How are you?\n" 125 | ] 126 | } 127 | ], 128 | "source": [ 129 | "def add_hi(func):\n", 130 | " def inner():\n", 131 | " print(\"Hi\")\n", 132 | " func()\n", 133 | " return inner\n", 134 | "\n", 135 | "\n", 136 | "def how_are_you():\n", 137 | " print(\"How are you?\")\n", 138 | " \n", 139 | "x = add_hi(how_are_you)\n", 140 | "x()" 141 | ] 142 | }, 143 | { 144 | "cell_type": "markdown", 145 | "metadata": {}, 146 | "source": [ 147 | "Python has a simplified syntax for this.\n", 148 | "\n", 149 | "We can use the @ symbol along with the name of the decorator function and place it above the definition of the function to be decorated." 150 | ] 151 | }, 152 | { 153 | "cell_type": "code", 154 | "execution_count": 7, 155 | "metadata": {}, 156 | "outputs": [ 157 | { 158 | "name": "stdout", 159 | "output_type": "stream", 160 | "text": [ 161 | "Hi\n", 162 | "How are you?\n" 163 | ] 164 | } 165 | ], 166 | "source": [ 167 | "@add_hi\n", 168 | "def how_are_you():\n", 169 | " print(\"How are you?\")\n", 170 | "\n", 171 | "how_are_you()" 172 | ] 173 | }, 174 | { 175 | "cell_type": "markdown", 176 | "metadata": {}, 177 | "source": [ 178 | "Access function arguments inside your decorator. For this lets take our CLI todo example." 179 | ] 180 | }, 181 | { 182 | "cell_type": "code", 183 | "execution_count": 15, 184 | "metadata": {}, 185 | "outputs": [ 186 | { 187 | "name": "stdout", 188 | "output_type": "stream", 189 | "text": [ 190 | "['hi']\n", 191 | "Your todo string should not contain any spaces.\n", 192 | "['hi']\n" 193 | ] 194 | }, 195 | { 196 | "data": { 197 | "text/plain": [ 198 | "['hi', 'hello']" 199 | ] 200 | }, 201 | "execution_count": 15, 202 | "metadata": {}, 203 | "output_type": "execute_result" 204 | } 205 | ], 206 | "source": [ 207 | "todo_list = []\n", 208 | "\n", 209 | "def validate_todo(func):\n", 210 | " def inner(list, val):\n", 211 | " if ' ' in val:\n", 212 | " print ('Your todo string should not contain any spaces.')\n", 213 | " return\n", 214 | " return func(list, val)\n", 215 | " return inner\n", 216 | "\n", 217 | "\n", 218 | "@validate_todo\n", 219 | "def add_todo(todo_list, val):\n", 220 | " todo_list.append(val)\n", 221 | " return todo_list\n", 222 | "\n", 223 | "add_todo(todo_list, 'hi')\n", 224 | "\n", 225 | "print (todo_list)\n", 226 | "\n", 227 | "add_todo(todo_list, 'h i')\n", 228 | "\n", 229 | "print (todo_list)\n", 230 | "\n", 231 | "add_todo(todo_list, 'hello')" 232 | ] 233 | }, 234 | { 235 | "cell_type": "markdown", 236 | "metadata": {}, 237 | "source": [ 238 | "# Iterators\n", 239 | "\n", 240 | "An iterator is an object that can be iterated (looped) upon. Iterators don’t compute the value of each item when instantiated. They only compute it when you ask for it. This is known as lazy evaluation.\n", 241 | "\n", 242 | "Lazy evaluation is useful when you have a very large data set to compute. It allows you to start using the data immediately, while the whole data set is being computed.\n", 243 | "\n", 244 | "We create iterator object using iter function." 245 | ] 246 | }, 247 | { 248 | "cell_type": "code", 249 | "execution_count": 3, 250 | "metadata": {}, 251 | "outputs": [ 252 | { 253 | "name": "stdout", 254 | "output_type": "stream", 255 | "text": [ 256 | "\n", 257 | "88\n", 258 | "56\n" 259 | ] 260 | } 261 | ], 262 | "source": [ 263 | "x = [1, 2, 3]\n", 264 | "y = iter(x)\n", 265 | "\n", 266 | "print (type(y))\n", 267 | "import sys\n", 268 | "print (sys.getsizeof(x))\n", 269 | "print (sys.getsizeof(y))" 270 | ] 271 | }, 272 | { 273 | "cell_type": "markdown", 274 | "metadata": {}, 275 | "source": [ 276 | "Here in this example x is called as iterable and y is iterator, how do we access the items of an iterator? We use next function to get the items of an iterator." 277 | ] 278 | }, 279 | { 280 | "cell_type": "code", 281 | "execution_count": 18, 282 | "metadata": {}, 283 | "outputs": [ 284 | { 285 | "name": "stdout", 286 | "output_type": "stream", 287 | "text": [ 288 | "1\n", 289 | "2\n", 290 | "3\n" 291 | ] 292 | } 293 | ], 294 | "source": [ 295 | "x = [1, 2, 3]\n", 296 | "y = iter(x)\n", 297 | "\n", 298 | "t = next(y)\n", 299 | "print (t)\n", 300 | "t = next(y)\n", 301 | "print (t)\n", 302 | "t = next(y)\n", 303 | "print (t)" 304 | ] 305 | }, 306 | { 307 | "cell_type": "markdown", 308 | "metadata": {}, 309 | "source": [ 310 | "Now we are at the end of the list iterator, so what happens when we still try to use next on this iterator? It will raise StopIteration exception i.e the iteration is finished or no elements remain in that iterator." 311 | ] 312 | }, 313 | { 314 | "cell_type": "code", 315 | "execution_count": 19, 316 | "metadata": {}, 317 | "outputs": [ 318 | { 319 | "name": "stdout", 320 | "output_type": "stream", 321 | "text": [ 322 | "1\n", 323 | "2\n", 324 | "3\n" 325 | ] 326 | }, 327 | { 328 | "ename": "StopIteration", 329 | "evalue": "", 330 | "output_type": "error", 331 | "traceback": [ 332 | "\u001b[0;31m---------------------------------------------------------------------------\u001b[0m", 333 | "\u001b[0;31mStopIteration\u001b[0m Traceback (most recent call last)", 334 | "\u001b[0;32m\u001b[0m in \u001b[0;36m\u001b[0;34m\u001b[0m\n\u001b[1;32m 8\u001b[0m \u001b[0mt\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mnext\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0my\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[1;32m 9\u001b[0m \u001b[0mprint\u001b[0m \u001b[0;34m(\u001b[0m\u001b[0mt\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0;32m---> 10\u001b[0;31m \u001b[0mt\u001b[0m \u001b[0;34m=\u001b[0m \u001b[0mnext\u001b[0m\u001b[0;34m(\u001b[0m\u001b[0my\u001b[0m\u001b[0;34m)\u001b[0m\u001b[0;34m\u001b[0m\u001b[0;34m\u001b[0m\u001b[0m\n\u001b[0m", 335 | "\u001b[0;31mStopIteration\u001b[0m: " 336 | ] 337 | } 338 | ], 339 | "source": [ 340 | "x = [1, 2, 3]\n", 341 | "y = iter(x)\n", 342 | "\n", 343 | "t = next(y)\n", 344 | "print (t)\n", 345 | "t = next(y)\n", 346 | "print (t)\n", 347 | "t = next(y)\n", 348 | "print (t)\n", 349 | "t = next(y)" 350 | ] 351 | }, 352 | { 353 | "cell_type": "markdown", 354 | "metadata": {}, 355 | "source": [ 356 | "There is another way to create iterator is using Classes we will discuss of how to create iterators using classes in next sessions." 357 | ] 358 | }, 359 | { 360 | "cell_type": "markdown", 361 | "metadata": {}, 362 | "source": [ 363 | "# Generator\n", 364 | "\n", 365 | "Generators are special functions that allow us to create iterators. So generally when we write a function we use return to return any value, if we use return that says the function execution is completed and it will return something. Generators use special keyword called yield to return a value. The magic yield is it holds that state of the function i.e it will continue to run where it is left." 366 | ] 367 | }, 368 | { 369 | "cell_type": "code", 370 | "execution_count": 4, 371 | "metadata": {}, 372 | "outputs": [ 373 | { 374 | "name": "stdout", 375 | "output_type": "stream", 376 | "text": [ 377 | "\n" 378 | ] 379 | } 380 | ], 381 | "source": [ 382 | "def even_nums(max):\n", 383 | " number = 0\n", 384 | " while number < max:\n", 385 | " number += 1\n", 386 | " if number%2 == 0:\n", 387 | " yield number\n", 388 | " \n", 389 | "evens = even_nums(10)\n", 390 | "print (evens)\n" 391 | ] 392 | }, 393 | { 394 | "cell_type": "code", 395 | "execution_count": 5, 396 | "metadata": {}, 397 | "outputs": [ 398 | { 399 | "name": "stdout", 400 | "output_type": "stream", 401 | "text": [ 402 | "2\n", 403 | "4\n", 404 | "6\n", 405 | "8\n", 406 | "10\n" 407 | ] 408 | } 409 | ], 410 | "source": [ 411 | "def even_nums(max):\n", 412 | " number = 0\n", 413 | " while number < max:\n", 414 | " number += 1\n", 415 | " if number%2 == 0:\n", 416 | " yield number\n", 417 | " \n", 418 | "\n", 419 | "for i in even_nums(10):\n", 420 | " print (i)" 421 | ] 422 | }, 423 | { 424 | "cell_type": "markdown", 425 | "metadata": {}, 426 | "source": [ 427 | "We can achieve the same with comprehensions. " 428 | ] 429 | }, 430 | { 431 | "cell_type": "code", 432 | "execution_count": 6, 433 | "metadata": {}, 434 | "outputs": [ 435 | { 436 | "name": "stdout", 437 | "output_type": "stream", 438 | "text": [ 439 | " at 0x7feaf050b360>\n", 440 | "[2, 4, 6, 8, 10]\n" 441 | ] 442 | } 443 | ], 444 | "source": [ 445 | "evens = (i for i in range(1, 11) if i%2==0)\n", 446 | "print (evens)\n", 447 | "print (list(evens))" 448 | ] 449 | }, 450 | { 451 | "cell_type": "markdown", 452 | "metadata": {}, 453 | "source": [ 454 | "# Debugging(pdb module)\n", 455 | "\n", 456 | "In any programming language, 'debugging' term is popularly used to process of locating and rectifying errors in a program. Python's standard library contains pdb module which is a set of utilities for debugging of Python programs." 457 | ] 458 | }, 459 | { 460 | "cell_type": "code", 461 | "execution_count": null, 462 | "metadata": {}, 463 | "outputs": [ 464 | { 465 | "name": "stdout", 466 | "output_type": "stream", 467 | "text": [ 468 | "--Return--\n", 469 | "> (3)()->None\n", 470 | "-> import pdb; pdb.set_trace()\n" 471 | ] 472 | } 473 | ], 474 | "source": [ 475 | "x = 1\n", 476 | "y = 2\n", 477 | "import pdb; pdb.set_trace()\n", 478 | "print(f'path = {x*y}')\n" 479 | ] 480 | }, 481 | { 482 | "cell_type": "markdown", 483 | "metadata": {}, 484 | "source": [ 485 | "Important options\n", 486 | "\n", 487 | "ll(long list)\n", 488 | "n(next)\n", 489 | "s(step)\n", 490 | "c(continue)" 491 | ] 492 | } 493 | ], 494 | "metadata": { 495 | "kernelspec": { 496 | "display_name": "Python 3", 497 | "language": "python", 498 | "name": "python3" 499 | }, 500 | "language_info": { 501 | "codemirror_mode": { 502 | "name": "ipython", 503 | "version": 3 504 | }, 505 | "file_extension": ".py", 506 | "mimetype": "text/x-python", 507 | "name": "python", 508 | "nbconvert_exporter": "python", 509 | "pygments_lexer": "ipython3", 510 | "version": "3.6.9" 511 | } 512 | }, 513 | "nbformat": 4, 514 | "nbformat_minor": 4 515 | } 516 | -------------------------------------------------------------------------------- /notebooks/8_packaging_vnenv.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "# Pypi & Pip\n", 8 | "\n", 9 | "PyPi is short form for Python Package Index (PyPI). PyPI helps you find and install open source software developed and shared by the Python community. All the python packages are distributed to python community through pypi.org . These packages are called as Distributed or intallable packages. To install any distributed or installable package we use command called Pip.\n", 10 | "\n" 11 | ] 12 | }, 13 | { 14 | "cell_type": "code", 15 | "execution_count": null, 16 | "metadata": {}, 17 | "outputs": [], 18 | "source": [ 19 | "pip install \n", 20 | "\n", 21 | "pip install requests" 22 | ] 23 | }, 24 | { 25 | "cell_type": "markdown", 26 | "metadata": {}, 27 | "source": [ 28 | "you can also specify which version of python package to install in the command." 29 | ] 30 | }, 31 | { 32 | "cell_type": "code", 33 | "execution_count": null, 34 | "metadata": {}, 35 | "outputs": [], 36 | "source": [ 37 | "pip install ==\n", 38 | "\n", 39 | "pip install requests==2.1.0" 40 | ] 41 | }, 42 | { 43 | "cell_type": "markdown", 44 | "metadata": {}, 45 | "source": [ 46 | "# How does pip install work?\n", 47 | "\n", 48 | "Every package/distribution that is being installed will have a setup.py. When you call pip install that is nothing but python setup.py build and python setup.py install\n", 49 | " \n", 50 | "What happens in this flow, with python setup.py build, it will download all the code of package to build folder installing any dependant packages, after that it will build a binary wheel specifically for your machine out of the source. Then it needs to determine which library directory to install the package in—the system's, the user's, or a virtualenv's? This is controlled by sys.prefix, which in turn is controlled by pip's executable path and the PYTHONPATH and PYTHONHOME environment variables. Finally, it moves the wheel files into the appropriate library directory, and compiles the python source files into bytecode for faster execution.\n", 51 | "\n" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": null, 57 | "metadata": {}, 58 | "outputs": [], 59 | "source": [ 60 | "# sample setup.py\n", 61 | "\n", 62 | "import os\n", 63 | "from setuptools import setup, find_packages\n", 64 | "\n", 65 | "setup(\n", 66 | " name='',\n", 67 | " version='0.3.1',\n", 68 | " packages=find_packages(exclude=['tests', 'tests.*']),\n", 69 | " include_package_data=True,\n", 70 | " description='A brief description of your package',\n", 71 | " long_description=README,\n", 72 | " url='',\n", 73 | " author='',\n", 74 | " author_email='',\n", 75 | " classifiers=[\n", 76 | " 'Environment :: Web Environment',\n", 77 | " 'Intended Audience :: Developers',\n", 78 | " 'Operating System :: OS Independent',\n", 79 | " 'License :: OSI Approved :: MIT License',\n", 80 | " 'Programming Language :: Python',\n", 81 | " 'Programming Language :: Python :: 2.7',\n", 82 | " 'Programming Language :: Python :: 3',\n", 83 | " 'Programming Language :: Python :: 3.2',\n", 84 | " 'Programming Language :: Python :: 3.3',\n", 85 | " ],\n", 86 | " install_requires=[\n", 87 | " \n", 88 | " ],\n", 89 | ")" 90 | ] 91 | }, 92 | { 93 | "cell_type": "markdown", 94 | "metadata": {}, 95 | "source": [ 96 | "# Virtualenv\n", 97 | "\n", 98 | "A Virtual Environment is an isolated working copy of Python which allows you to work on a specific project without worry of affecting other projects. It enables multiple side-by-side installations of Python, one for each project. Following are the commands to install virtualenv." 99 | ] 100 | }, 101 | { 102 | "cell_type": "markdown", 103 | "metadata": {}, 104 | "source": [ 105 | "On macOS and Linux:" 106 | ] 107 | }, 108 | { 109 | "cell_type": "code", 110 | "execution_count": null, 111 | "metadata": {}, 112 | "outputs": [], 113 | "source": [ 114 | "python3 -m pip install --user virtualenv" 115 | ] 116 | }, 117 | { 118 | "cell_type": "markdown", 119 | "metadata": {}, 120 | "source": [ 121 | "On Windows:" 122 | ] 123 | }, 124 | { 125 | "cell_type": "code", 126 | "execution_count": null, 127 | "metadata": {}, 128 | "outputs": [], 129 | "source": [ 130 | "py -m pip install --user virtualenv" 131 | ] 132 | }, 133 | { 134 | "cell_type": "markdown", 135 | "metadata": {}, 136 | "source": [ 137 | "We create vitrualenv using the following commands" 138 | ] 139 | }, 140 | { 141 | "cell_type": "markdown", 142 | "metadata": {}, 143 | "source": [ 144 | "On macOS and Linux:" 145 | ] 146 | }, 147 | { 148 | "cell_type": "code", 149 | "execution_count": null, 150 | "metadata": {}, 151 | "outputs": [], 152 | "source": [ 153 | "python3 -m venv env" 154 | ] 155 | }, 156 | { 157 | "cell_type": "markdown", 158 | "metadata": {}, 159 | "source": [ 160 | "On Windows:" 161 | ] 162 | }, 163 | { 164 | "cell_type": "code", 165 | "execution_count": null, 166 | "metadata": {}, 167 | "outputs": [], 168 | "source": [ 169 | "py -m venv env" 170 | ] 171 | }, 172 | { 173 | "cell_type": "markdown", 174 | "metadata": {}, 175 | "source": [ 176 | "Before you can start installing or using packages in your virtual environment you’ll need to activate it. To activate the environment use the following commands\n", 177 | "\n", 178 | "On macOS and Linux:" 179 | ] 180 | }, 181 | { 182 | "cell_type": "code", 183 | "execution_count": null, 184 | "metadata": {}, 185 | "outputs": [], 186 | "source": [ 187 | "source env/bin/activate" 188 | ] 189 | }, 190 | { 191 | "cell_type": "markdown", 192 | "metadata": {}, 193 | "source": [ 194 | "On Windows:" 195 | ] 196 | }, 197 | { 198 | "cell_type": "code", 199 | "execution_count": null, 200 | "metadata": {}, 201 | "outputs": [], 202 | "source": [ 203 | ".\\env\\Scripts\\activate" 204 | ] 205 | }, 206 | { 207 | "cell_type": "markdown", 208 | "metadata": {}, 209 | "source": [ 210 | "Following are some important commands when we use virtualenv\n", 211 | "\n", 212 | "> pip freeze\n", 213 | " shows packages YOU installed via pip in that environment\n", 214 | "> pip freeze > requirements.txt\n", 215 | " used to write the installed packages into the file.\n", 216 | "> pip install -r requrements.txt\n", 217 | " Used to install all the packages inside requirements" 218 | ] 219 | }, 220 | { 221 | "cell_type": "markdown", 222 | "metadata": {}, 223 | "source": [ 224 | "# Create your own package\n", 225 | "\n", 226 | "We will see how to publish a simple helloworld as a pypi package. I'm creating a simple package with hellow as a folder and to make it a package I'm adding __init__.py to it.\n", 227 | "\n", 228 | "Inside that folder I'm creating a simple file called greeting and inside my greeting file, I'm adding a simple function called hello_world that prints hello_world\n" 229 | ] 230 | }, 231 | { 232 | "cell_type": "code", 233 | "execution_count": null, 234 | "metadata": {}, 235 | "outputs": [], 236 | "source": [ 237 | "helloworld/\n", 238 | "├── hellow\n", 239 | "   ├── __init__.py\n", 240 | "   └── greeting.py\n", 241 | "\n", 242 | "\n", 243 | "1 directory, 2 files" 244 | ] 245 | }, 246 | { 247 | "cell_type": "code", 248 | "execution_count": null, 249 | "metadata": {}, 250 | "outputs": [], 251 | "source": [ 252 | "# in greeting.py\n", 253 | "\n", 254 | "def hello_world():\n", 255 | " print (\"hello world\")\n" 256 | ] 257 | }, 258 | { 259 | "cell_type": "markdown", 260 | "metadata": {}, 261 | "source": [ 262 | "As discussed earlier we need setup.py file to make a python package into a distributed package. So I'm creating a setup.py file parallet to hellow folder. In my setup.py I'll add corresponding information required for that package." 263 | ] 264 | }, 265 | { 266 | "cell_type": "code", 267 | "execution_count": null, 268 | "metadata": {}, 269 | "outputs": [], 270 | "source": [ 271 | "├── hellow\n", 272 | "│   ├── __init__.py\n", 273 | "│   └── greeting.py\n", 274 | "└── setup.py\n", 275 | "\n", 276 | "1 directory, 3 files\n" 277 | ] 278 | }, 279 | { 280 | "cell_type": "code", 281 | "execution_count": null, 282 | "metadata": {}, 283 | "outputs": [], 284 | "source": [ 285 | "# in setup.py\n", 286 | "\n", 287 | "import os\n", 288 | "from setuptools import setup, find_packages\n", 289 | "\n", 290 | "setup(\n", 291 | " name='chaitu_210_hw_greeting',\n", 292 | " version='1.0',\n", 293 | " packages=['hellow'],\n", 294 | " include_package_data=True,\n", 295 | " description='A brief description of your package',\n", 296 | " long_description='',\n", 297 | " url='https://www.test.com/',\n", 298 | " author='chaitanya',\n", 299 | " author_email='chaitu210@gmail.com',\n", 300 | " classifiers=[\n", 301 | " 'Environment :: Web Environment',\n", 302 | " 'Intended Audience :: Developers',\n", 303 | " 'Operating System :: OS Independent',\n", 304 | " 'License :: OSI Approved :: MIT License',\n", 305 | " 'Programming Language :: Python',\n", 306 | " 'Programming Language :: Python :: 2.7',\n", 307 | " 'Programming Language :: Python :: 3',\n", 308 | " 'Programming Language :: Python :: 3.2',\n", 309 | " 'Programming Language :: Python :: 3.3',\n", 310 | " ],\n", 311 | " install_requires=[\n", 312 | " ],\n", 313 | ")\n", 314 | "\n" 315 | ] 316 | }, 317 | { 318 | "cell_type": "markdown", 319 | "metadata": {}, 320 | "source": [ 321 | "Before make our python package as a distributed package, we will create an account in pypi.org, you can create an using the following link \n", 322 | "\n", 323 | "https://pypi.org/account/register/" 324 | ] 325 | }, 326 | { 327 | "cell_type": "markdown", 328 | "metadata": {}, 329 | "source": [ 330 | "Now to upload our package we run the following commands" 331 | ] 332 | }, 333 | { 334 | "cell_type": "code", 335 | "execution_count": null, 336 | "metadata": {}, 337 | "outputs": [], 338 | "source": [ 339 | "> python setup.py bdist_wheel sdist\n", 340 | "> pip install twine\n", 341 | "> twine upload dist/*" 342 | ] 343 | }, 344 | { 345 | "cell_type": "markdown", 346 | "metadata": {}, 347 | "source": [ 348 | "On running the last command it will ask for your pypi username and password. On successful upload we are now ready to use the package in any other project or any python developer can install the package using \n", 349 | "\n", 350 | "pip install chaitu_210_hw_greeting" 351 | ] 352 | }, 353 | { 354 | "cell_type": "markdown", 355 | "metadata": {}, 356 | "source": [ 357 | "There are more options that we can research while create a package for Eg: Manifest.in, docs, README.md etc.\n", 358 | "\n", 359 | "Manifest.in : Used for adding the non python files like htmls\n", 360 | "Docs: If your package has more documentation you will use this.\n", 361 | "README.md: This is used to give detailed description/usage about your package." 362 | ] 363 | } 364 | ], 365 | "metadata": { 366 | "kernelspec": { 367 | "display_name": "Python 3", 368 | "language": "python", 369 | "name": "python3" 370 | }, 371 | "language_info": { 372 | "codemirror_mode": { 373 | "name": "ipython", 374 | "version": 3 375 | }, 376 | "file_extension": ".py", 377 | "mimetype": "text/x-python", 378 | "name": "python", 379 | "nbconvert_exporter": "python", 380 | "pygments_lexer": "ipython3", 381 | "version": "3.7.5" 382 | } 383 | }, 384 | "nbformat": 4, 385 | "nbformat_minor": 4 386 | } 387 | -------------------------------------------------------------------------------- /notes: -------------------------------------------------------------------------------- 1 | tuple unpacking 2 | dynamic and static typing 3 | --------------------------------------------------------------------------------