├── 002_Organizing_Larger_Programs ├── 001_Packages.ipynb ├── 002_Creating Packages.ipynb ├── 003_Dunder All and Namespace packages.ipynb ├── 004_Executable Directories.ipynb ├── farm │ ├── path1 │ │ └── split_farm │ │ │ └── bovine │ │ │ ├── __init__.py │ │ │ ├── common.py │ │ │ ├── cow.py │ │ │ ├── ox.py │ │ │ └── string.py │ └── path2 │ │ └── split_farm │ │ └── bird │ │ ├── __init__.py │ │ ├── chicken.py │ │ └── turkey.py ├── folder2_for_001 │ └── hello2.py ├── folder_for_001 │ └── hello.py ├── reader.zip ├── reader │ ├── __main__.py │ └── reader │ │ ├── __init__.py │ │ ├── compressed │ │ ├── __init__.py │ │ ├── bzipped.py │ │ └── gzipped.py │ │ └── reader.py ├── test.bz2 ├── test.file └── test.gz2 ├── 003_Beyond_Basic_Functions ├── 001_Function Review.ipynb ├── 002_Callable Instances.ipynb ├── 003_Lambdas.ipynb ├── 004_Extended Formal Arguments.ipynb └── lamda_diff.jpg ├── 004_Closures_and_Decorators ├── 001_LEGB Scope Rules.ipynb ├── 002_Closures and Function Factories.ipynb └── 003_Decorators.ipynb ├── 005_Class_Methods ├── 001_Class and Static Methods.ipynb ├── ShippingContainers.py ├── iso6346.py └── static_vs_class.png ├── 006_String and Representations └── 001_Using __str__, __repr__.ipynb ├── 007_Numeric and scalar datatypes └── 001_Numbers.ipynb ├── 008_Iterables and Iteration ├── 001_Comprehensions, map(), filter(), reduce().ipynb ├── 002_Iterables and Iteration.ipynb └── map_reduce │ └── map_reduce.py ├── 009_Inheritance and Subtype Polymorphism ├── 001_Multiple Inheritance.ipynb ├── sorted_list.py └── super.png ├── README.md └── _config.yml /002_Organizing_Larger_Programs/001_Packages.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Importing modules" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 1, 13 | "metadata": { 14 | "collapsed": true 15 | }, 16 | "outputs": [], 17 | "source": [ 18 | "import urllib" 19 | ] 20 | }, 21 | { 22 | "cell_type": "code", 23 | "execution_count": 2, 24 | "metadata": { 25 | "collapsed": false 26 | }, 27 | "outputs": [ 28 | { 29 | "data": { 30 | "text/plain": [ 31 | "module" 32 | ] 33 | }, 34 | "execution_count": 2, 35 | "metadata": {}, 36 | "output_type": "execute_result" 37 | } 38 | ], 39 | "source": [ 40 | "type(urllib)" 41 | ] 42 | }, 43 | { 44 | "cell_type": "code", 45 | "execution_count": 3, 46 | "metadata": { 47 | "collapsed": true 48 | }, 49 | "outputs": [], 50 | "source": [ 51 | "import urllib.request" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 4, 57 | "metadata": { 58 | "collapsed": false 59 | }, 60 | "outputs": [ 61 | { 62 | "data": { 63 | "text/plain": [ 64 | "module" 65 | ] 66 | }, 67 | "execution_count": 4, 68 | "metadata": {}, 69 | "output_type": "execute_result" 70 | } 71 | ], 72 | "source": [ 73 | "type(urllib.request)" 74 | ] 75 | }, 76 | { 77 | "cell_type": "code", 78 | "execution_count": 5, 79 | "metadata": { 80 | "collapsed": false 81 | }, 82 | "outputs": [ 83 | { 84 | "data": { 85 | "text/plain": [ 86 | "['/home/deen/anaconda3/lib/python3.5/urllib']" 87 | ] 88 | }, 89 | "execution_count": 5, 90 | "metadata": {}, 91 | "output_type": "execute_result" 92 | } 93 | ], 94 | "source": [ 95 | "# Getting path \n", 96 | "urllib.__path__" 97 | ] 98 | }, 99 | { 100 | "cell_type": "code", 101 | "execution_count": 6, 102 | "metadata": { 103 | "collapsed": false 104 | }, 105 | "outputs": [ 106 | { 107 | "name": "stdout", 108 | "output_type": "stream", 109 | "text": [ 110 | "Not a package\n" 111 | ] 112 | } 113 | ], 114 | "source": [ 115 | "try:\n", 116 | " print(urllib.request.__path__)\n", 117 | "except:\n", 118 | " print('Not a package')" 119 | ] 120 | }, 121 | { 122 | "cell_type": "markdown", 123 | "metadata": {}, 124 | "source": [ 125 | "### Note:\n", 126 | "Packages are generally directories \n", 127 | "Modules are generally files" 128 | ] 129 | }, 130 | { 131 | "cell_type": "markdown", 132 | "metadata": {}, 133 | "source": [ 134 | "## Getting PATHs" 135 | ] 136 | }, 137 | { 138 | "cell_type": "code", 139 | "execution_count": 7, 140 | "metadata": { 141 | "collapsed": true 142 | }, 143 | "outputs": [], 144 | "source": [ 145 | "import sys" 146 | ] 147 | }, 148 | { 149 | "cell_type": "code", 150 | "execution_count": 8, 151 | "metadata": { 152 | "collapsed": false 153 | }, 154 | "outputs": [ 155 | { 156 | "name": "stdout", 157 | "output_type": "stream", 158 | "text": [ 159 | "['', '/home/deen/anaconda3/lib/python35.zip', '/home/deen/anaconda3/lib/python3.5', '/home/deen/anaconda3/lib/python3.5/plat-linux', '/home/deen/anaconda3/lib/python3.5/lib-dynload', '/home/deen/anaconda3/lib/python3.5/site-packages', '/home/deen/anaconda3/lib/python3.5/site-packages/Sphinx-1.4.6-py3.5.egg', '/home/deen/anaconda3/lib/python3.5/site-packages/setuptools-27.2.0-py3.5.egg', '/home/deen/anaconda3/lib/python3.5/site-packages/IPython/extensions', '/home/deen/.ipython']\n" 160 | ] 161 | } 162 | ], 163 | "source": [ 164 | "print(sys.path)" 165 | ] 166 | }, 167 | { 168 | "cell_type": "markdown", 169 | "metadata": {}, 170 | "source": [ 171 | "### Sys.path is a list and can be indexed" 172 | ] 173 | }, 174 | { 175 | "cell_type": "code", 176 | "execution_count": 10, 177 | "metadata": { 178 | "collapsed": false 179 | }, 180 | "outputs": [ 181 | { 182 | "data": { 183 | "text/plain": [ 184 | "list" 185 | ] 186 | }, 187 | "execution_count": 10, 188 | "metadata": {}, 189 | "output_type": "execute_result" 190 | } 191 | ], 192 | "source": [ 193 | "type(sys.path)" 194 | ] 195 | }, 196 | { 197 | "cell_type": "code", 198 | "execution_count": 13, 199 | "metadata": { 200 | "collapsed": false 201 | }, 202 | "outputs": [ 203 | { 204 | "name": "stdout", 205 | "output_type": "stream", 206 | "text": [ 207 | "\n", 208 | "['/home/deen/anaconda3/lib/python3.5/site-packages/IPython/extensions', '/home/deen/.ipython']\n" 209 | ] 210 | } 211 | ], 212 | "source": [ 213 | "print(sys.path[0])\n", 214 | "print(sys.path[-2:])" 215 | ] 216 | }, 217 | { 218 | "cell_type": "markdown", 219 | "metadata": { 220 | "collapsed": true 221 | }, 222 | "source": [ 223 | "### Appending path to sys.path" 224 | ] 225 | }, 226 | { 227 | "cell_type": "code", 228 | "execution_count": 14, 229 | "metadata": { 230 | "collapsed": true 231 | }, 232 | "outputs": [], 233 | "source": [ 234 | "# sys.path is a list remember therefore all list functions work\n", 235 | "sys.path.append('folder_for_001/')" 236 | ] 237 | }, 238 | { 239 | "cell_type": "code", 240 | "execution_count": 24, 241 | "metadata": { 242 | "collapsed": false 243 | }, 244 | "outputs": [ 245 | { 246 | "data": { 247 | "text/plain": [ 248 | "'folder_for_001/hello.py'" 249 | ] 250 | }, 251 | "execution_count": 24, 252 | "metadata": {}, 253 | "output_type": "execute_result" 254 | } 255 | ], 256 | "source": [ 257 | "import hello\n", 258 | "hello.__file__" 259 | ] 260 | }, 261 | { 262 | "cell_type": "code", 263 | "execution_count": 18, 264 | "metadata": { 265 | "collapsed": false 266 | }, 267 | "outputs": [ 268 | { 269 | "name": "stdout", 270 | "output_type": "stream", 271 | "text": [ 272 | "Hello from folder in path var\n" 273 | ] 274 | } 275 | ], 276 | "source": [ 277 | "hello.hello()" 278 | ] 279 | } 280 | ], 281 | "metadata": { 282 | "kernelspec": { 283 | "display_name": "Python [conda root]", 284 | "language": "python", 285 | "name": "conda-root-py" 286 | }, 287 | "language_info": { 288 | "codemirror_mode": { 289 | "name": "ipython", 290 | "version": 3 291 | }, 292 | "file_extension": ".py", 293 | "mimetype": "text/x-python", 294 | "name": "python", 295 | "nbconvert_exporter": "python", 296 | "pygments_lexer": "ipython3", 297 | "version": "3.5.2" 298 | } 299 | }, 300 | "nbformat": 4, 301 | "nbformat_minor": 1 302 | } 303 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/002_Creating Packages.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Steps to creating a new package" 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "1. Create a directory\n", 15 | "2. touch file __init__.py\n", 16 | "3. Create module files\n", 17 | "4. Add import statments in __init__.py to make imports easier" 18 | ] 19 | }, 20 | { 21 | "cell_type": "code", 22 | "execution_count": 1, 23 | "metadata": { 24 | "collapsed": false 25 | }, 26 | "outputs": [ 27 | { 28 | "name": "stdout", 29 | "output_type": "stream", 30 | "text": [ 31 | "Importing pkg...\n" 32 | ] 33 | } 34 | ], 35 | "source": [ 36 | "# Importing the package\n", 37 | "import reader" 38 | ] 39 | }, 40 | { 41 | "cell_type": "code", 42 | "execution_count": 2, 43 | "metadata": { 44 | "collapsed": false 45 | }, 46 | "outputs": [ 47 | { 48 | "data": { 49 | "text/plain": [ 50 | "module" 51 | ] 52 | }, 53 | "execution_count": 2, 54 | "metadata": {}, 55 | "output_type": "execute_result" 56 | } 57 | ], 58 | "source": [ 59 | "type(reader)" 60 | ] 61 | }, 62 | { 63 | "cell_type": "markdown", 64 | "metadata": {}, 65 | "source": [ 66 | "## Creating new file" 67 | ] 68 | }, 69 | { 70 | "cell_type": "code", 71 | "execution_count": 1, 72 | "metadata": { 73 | "collapsed": false 74 | }, 75 | "outputs": [ 76 | { 77 | "name": "stdout", 78 | "output_type": "stream", 79 | "text": [ 80 | "Importing pkg...\n" 81 | ] 82 | } 83 | ], 84 | "source": [ 85 | "import reader" 86 | ] 87 | }, 88 | { 89 | "cell_type": "code", 90 | "execution_count": 2, 91 | "metadata": { 92 | "collapsed": false 93 | }, 94 | "outputs": [ 95 | { 96 | "data": { 97 | "text/plain": [ 98 | "'/home/deen/Code/Python/Python Beyond the Basics/reader/__init__.py'" 99 | ] 100 | }, 101 | "execution_count": 2, 102 | "metadata": {}, 103 | "output_type": "execute_result" 104 | } 105 | ], 106 | "source": [ 107 | "reader.__file__" 108 | ] 109 | }, 110 | { 111 | "cell_type": "code", 112 | "execution_count": 5, 113 | "metadata": { 114 | "collapsed": true 115 | }, 116 | "outputs": [], 117 | "source": [ 118 | "from reader.reader import Reader" 119 | ] 120 | }, 121 | { 122 | "cell_type": "code", 123 | "execution_count": 8, 124 | "metadata": { 125 | "collapsed": false 126 | }, 127 | "outputs": [], 128 | "source": [ 129 | "r = reader.reader.Reader('test.file')" 130 | ] 131 | }, 132 | { 133 | "cell_type": "code", 134 | "execution_count": 13, 135 | "metadata": { 136 | "collapsed": false 137 | }, 138 | "outputs": [ 139 | { 140 | "name": "stdout", 141 | "output_type": "stream", 142 | "text": [ 143 | "Hello from test.file\n", 144 | "\n" 145 | ] 146 | } 147 | ], 148 | "source": [ 149 | "print(r.read())" 150 | ] 151 | }, 152 | { 153 | "cell_type": "markdown", 154 | "metadata": {}, 155 | "source": [ 156 | "## Using imports in __init__.py" 157 | ] 158 | }, 159 | { 160 | "cell_type": "code", 161 | "execution_count": 1, 162 | "metadata": { 163 | "collapsed": false 164 | }, 165 | "outputs": [ 166 | { 167 | "name": "stdout", 168 | "output_type": "stream", 169 | "text": [ 170 | "Importing pkg...\n" 171 | ] 172 | } 173 | ], 174 | "source": [ 175 | "import reader" 176 | ] 177 | }, 178 | { 179 | "cell_type": "code", 180 | "execution_count": 3, 181 | "metadata": { 182 | "collapsed": false 183 | }, 184 | "outputs": [], 185 | "source": [ 186 | "r = reader.Reader('test.file')" 187 | ] 188 | }, 189 | { 190 | "cell_type": "code", 191 | "execution_count": 4, 192 | "metadata": { 193 | "collapsed": false 194 | }, 195 | "outputs": [ 196 | { 197 | "name": "stdout", 198 | "output_type": "stream", 199 | "text": [ 200 | "Hello from test.file\n", 201 | "\n" 202 | ] 203 | } 204 | ], 205 | "source": [ 206 | "print(r.read())" 207 | ] 208 | }, 209 | { 210 | "cell_type": "code", 211 | "execution_count": 5, 212 | "metadata": { 213 | "collapsed": true 214 | }, 215 | "outputs": [], 216 | "source": [ 217 | "r.close()" 218 | ] 219 | }, 220 | { 221 | "cell_type": "markdown", 222 | "metadata": {}, 223 | "source": [ 224 | "## Having subpackages" 225 | ] 226 | }, 227 | { 228 | "cell_type": "code", 229 | "execution_count": 1, 230 | "metadata": { 231 | "collapsed": false 232 | }, 233 | "outputs": [ 234 | { 235 | "name": "stdout", 236 | "output_type": "stream", 237 | "text": [ 238 | "Importing pkg...\n", 239 | "Importing compressed package\n" 240 | ] 241 | } 242 | ], 243 | "source": [ 244 | "import reader.compressed" 245 | ] 246 | }, 247 | { 248 | "cell_type": "markdown", 249 | "metadata": { 250 | "collapsed": true 251 | }, 252 | "source": [ 253 | "## The whole package" 254 | ] 255 | }, 256 | { 257 | "cell_type": "code", 258 | "execution_count": 1, 259 | "metadata": { 260 | "collapsed": false 261 | }, 262 | "outputs": [ 263 | { 264 | "name": "stdout", 265 | "output_type": "stream", 266 | "text": [ 267 | "Importing pkg...\n", 268 | "Importing compressed package...\n" 269 | ] 270 | } 271 | ], 272 | "source": [ 273 | "import reader" 274 | ] 275 | }, 276 | { 277 | "cell_type": "code", 278 | "execution_count": 2, 279 | "metadata": { 280 | "collapsed": true 281 | }, 282 | "outputs": [], 283 | "source": [ 284 | "r = reader.Reader('test.bz2')" 285 | ] 286 | }, 287 | { 288 | "cell_type": "code", 289 | "execution_count": 3, 290 | "metadata": { 291 | "collapsed": false 292 | }, 293 | "outputs": [ 294 | { 295 | "data": { 296 | "text/plain": [ 297 | "'datacompressedwithbunzip'" 298 | ] 299 | }, 300 | "execution_count": 3, 301 | "metadata": {}, 302 | "output_type": "execute_result" 303 | } 304 | ], 305 | "source": [ 306 | "r.read()" 307 | ] 308 | }, 309 | { 310 | "cell_type": "code", 311 | "execution_count": 4, 312 | "metadata": { 313 | "collapsed": true 314 | }, 315 | "outputs": [], 316 | "source": [ 317 | "r.close()" 318 | ] 319 | }, 320 | { 321 | "cell_type": "code", 322 | "execution_count": 5, 323 | "metadata": { 324 | "collapsed": true 325 | }, 326 | "outputs": [], 327 | "source": [ 328 | "r = reader.Reader('test.gz2')" 329 | ] 330 | }, 331 | { 332 | "cell_type": "code", 333 | "execution_count": 6, 334 | "metadata": { 335 | "collapsed": false 336 | }, 337 | "outputs": [ 338 | { 339 | "data": { 340 | "text/plain": [ 341 | "'compressedwithgunzip'" 342 | ] 343 | }, 344 | "execution_count": 6, 345 | "metadata": {}, 346 | "output_type": "execute_result" 347 | } 348 | ], 349 | "source": [ 350 | "r.read()" 351 | ] 352 | }, 353 | { 354 | "cell_type": "code", 355 | "execution_count": 7, 356 | "metadata": { 357 | "collapsed": true 358 | }, 359 | "outputs": [], 360 | "source": [ 361 | "r.close()" 362 | ] 363 | }, 364 | { 365 | "cell_type": "code", 366 | "execution_count": 8, 367 | "metadata": { 368 | "collapsed": true 369 | }, 370 | "outputs": [], 371 | "source": [ 372 | "r = reader.Reader('test.file')" 373 | ] 374 | }, 375 | { 376 | "cell_type": "code", 377 | "execution_count": 9, 378 | "metadata": { 379 | "collapsed": false 380 | }, 381 | "outputs": [ 382 | { 383 | "data": { 384 | "text/plain": [ 385 | "'Hello from test.file\\n'" 386 | ] 387 | }, 388 | "execution_count": 9, 389 | "metadata": {}, 390 | "output_type": "execute_result" 391 | } 392 | ], 393 | "source": [ 394 | "r.read()" 395 | ] 396 | }, 397 | { 398 | "cell_type": "code", 399 | "execution_count": 11, 400 | "metadata": { 401 | "collapsed": false 402 | }, 403 | "outputs": [], 404 | "source": [ 405 | "r.close()" 406 | ] 407 | }, 408 | { 409 | "cell_type": "markdown", 410 | "metadata": {}, 411 | "source": [ 412 | "## Review\n", 413 | "\n", 414 | "1. Packages are modules that contain other modules.\n", 415 | "2. Packages are generally directories containing the special 'init' file.\n", 416 | "3. The dunder-init-dunder.py file is executed when package is imported.\n", 417 | "4. Packages may contain subpackages.\n", 418 | "5. These subpackages may themselves have their own init files" 419 | ] 420 | }, 421 | { 422 | "cell_type": "code", 423 | "execution_count": null, 424 | "metadata": { 425 | "collapsed": true 426 | }, 427 | "outputs": [], 428 | "source": [] 429 | } 430 | ], 431 | "metadata": { 432 | "kernelspec": { 433 | "display_name": "Python [conda root]", 434 | "language": "python", 435 | "name": "conda-root-py" 436 | }, 437 | "language_info": { 438 | "codemirror_mode": { 439 | "name": "ipython", 440 | "version": 3 441 | }, 442 | "file_extension": ".py", 443 | "mimetype": "text/x-python", 444 | "name": "python", 445 | "nbconvert_exporter": "python", 446 | "pygments_lexer": "ipython3", 447 | "version": "3.5.2" 448 | } 449 | }, 450 | "nbformat": 4, 451 | "nbformat_minor": 1 452 | } 453 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/003_Dunder All and Namespace packages.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## \\__all__ " 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "1. To import specific Classes/ Functions use \\__all__\n", 15 | "2. If \\__all__ is not specified, `from module import *` will import all modules and classes\n", 16 | "3. \\__all__ is a `list` of `str` containing what functions/ modules to import" 17 | ] 18 | }, 19 | { 20 | "cell_type": "code", 21 | "execution_count": 1, 22 | "metadata": { 23 | "collapsed": false 24 | }, 25 | "outputs": [ 26 | { 27 | "data": { 28 | "text/plain": [ 29 | "{'In': ['', 'locals()'],\n", 30 | " 'Out': {},\n", 31 | " '_': '',\n", 32 | " '__': '',\n", 33 | " '___': '',\n", 34 | " '__builtin__': ,\n", 35 | " '__builtins__': ,\n", 36 | " '__doc__': 'Automatically created module for IPython interactive environment',\n", 37 | " '__loader__': None,\n", 38 | " '__name__': '__main__',\n", 39 | " '__package__': None,\n", 40 | " '__spec__': None,\n", 41 | " '_dh': ['/home/deen/Code/Python/Python Beyond the Basics'],\n", 42 | " '_i': '',\n", 43 | " '_i1': 'locals()',\n", 44 | " '_ih': ['', 'locals()'],\n", 45 | " '_ii': '',\n", 46 | " '_iii': '',\n", 47 | " '_oh': {},\n", 48 | " '_sh': ,\n", 49 | " 'exit': ,\n", 50 | " 'get_ipython': >,\n", 51 | " 'quit': }" 52 | ] 53 | }, 54 | "execution_count": 1, 55 | "metadata": {}, 56 | "output_type": "execute_result" 57 | } 58 | ], 59 | "source": [ 60 | "# locals() gives a dict mapping local vars to \n", 61 | "locals()" 62 | ] 63 | }, 64 | { 65 | "cell_type": "code", 66 | "execution_count": 2, 67 | "metadata": { 68 | "collapsed": false 69 | }, 70 | "outputs": [ 71 | { 72 | "name": "stdout", 73 | "output_type": "stream", 74 | "text": [ 75 | "Importing compressed package...\n", 76 | "Importing pkg...\n" 77 | ] 78 | } 79 | ], 80 | "source": [ 81 | "from reader.compressed import *" 82 | ] 83 | }, 84 | { 85 | "cell_type": "code", 86 | "execution_count": 3, 87 | "metadata": { 88 | "collapsed": false 89 | }, 90 | "outputs": [ 91 | { 92 | "data": { 93 | "text/plain": [ 94 | "{'In': ['', 'locals()', 'from reader.compressed import *', 'locals()'],\n", 95 | " 'Out': {1: {...}},\n", 96 | " '_': {...},\n", 97 | " '_1': {...},\n", 98 | " '__': '',\n", 99 | " '___': '',\n", 100 | " '__builtin__': ,\n", 101 | " '__builtins__': ,\n", 102 | " '__doc__': 'Automatically created module for IPython interactive environment',\n", 103 | " '__loader__': None,\n", 104 | " '__name__': '__main__',\n", 105 | " '__package__': None,\n", 106 | " '__spec__': None,\n", 107 | " '_dh': ['/home/deen/Code/Python/Python Beyond the Basics'],\n", 108 | " '_i': 'from reader.compressed import *',\n", 109 | " '_i1': 'locals()',\n", 110 | " '_i2': 'from reader.compressed import *',\n", 111 | " '_i3': 'locals()',\n", 112 | " '_ih': ['', 'locals()', 'from reader.compressed import *', 'locals()'],\n", 113 | " '_ii': 'locals()',\n", 114 | " '_iii': '',\n", 115 | " '_oh': {1: {...}},\n", 116 | " '_sh': ,\n", 117 | " 'bzipped': ,\n", 118 | " 'exit': ,\n", 119 | " 'get_ipython': >,\n", 120 | " 'gzipped': ,\n", 121 | " 'quit': }" 122 | ] 123 | }, 124 | "execution_count": 3, 125 | "metadata": {}, 126 | "output_type": "execute_result" 127 | } 128 | ], 129 | "source": [ 130 | "locals()" 131 | ] 132 | }, 133 | { 134 | "cell_type": "code", 135 | "execution_count": 4, 136 | "metadata": { 137 | "collapsed": false 138 | }, 139 | "outputs": [ 140 | { 141 | "name": "stdout", 142 | "output_type": "stream", 143 | "text": [ 144 | "\n", 145 | "\n" 146 | ] 147 | } 148 | ], 149 | "source": [ 150 | "print(bzipped)\n", 151 | "print(gzipped)" 152 | ] 153 | }, 154 | { 155 | "cell_type": "markdown", 156 | "metadata": {}, 157 | "source": [ 158 | "### Here the complete module is imported to import only the OPENER function use \\__all__" 159 | ] 160 | }, 161 | { 162 | "cell_type": "code", 163 | "execution_count": 1, 164 | "metadata": { 165 | "collapsed": true 166 | }, 167 | "outputs": [], 168 | "source": [ 169 | "from reader.compressed import *" 170 | ] 171 | }, 172 | { 173 | "cell_type": "code", 174 | "execution_count": 2, 175 | "metadata": { 176 | "collapsed": false 177 | }, 178 | "outputs": [ 179 | { 180 | "data": { 181 | "text/plain": [ 182 | "{'In': ['', 'from reader.compressed import *', 'locals()'],\n", 183 | " 'Out': {},\n", 184 | " '_': '',\n", 185 | " '__': '',\n", 186 | " '___': '',\n", 187 | " '__builtin__': ,\n", 188 | " '__builtins__': ,\n", 189 | " '__doc__': 'Automatically created module for IPython interactive environment',\n", 190 | " '__loader__': None,\n", 191 | " '__name__': '__main__',\n", 192 | " '__package__': None,\n", 193 | " '__spec__': None,\n", 194 | " '_dh': ['/home/deen/Code/Python/Python Beyond the Basics'],\n", 195 | " '_i': 'from reader.compressed import *',\n", 196 | " '_i1': 'from reader.compressed import *',\n", 197 | " '_i2': 'locals()',\n", 198 | " '_ih': ['', 'from reader.compressed import *', 'locals()'],\n", 199 | " '_ii': '',\n", 200 | " '_iii': '',\n", 201 | " '_oh': {},\n", 202 | " '_sh': ,\n", 203 | " 'bz2_opener': ,\n", 204 | " 'exit': ,\n", 205 | " 'get_ipython': >,\n", 206 | " 'gz2_opener': ,\n", 207 | " 'quit': }" 208 | ] 209 | }, 210 | "execution_count": 2, 211 | "metadata": {}, 212 | "output_type": "execute_result" 213 | } 214 | ], 215 | "source": [ 216 | "locals()" 217 | ] 218 | }, 219 | { 220 | "cell_type": "markdown", 221 | "metadata": {}, 222 | "source": [ 223 | "### Note:\n", 224 | "Now only the opener functions are imported" 225 | ] 226 | }, 227 | { 228 | "cell_type": "code", 229 | "execution_count": 3, 230 | "metadata": { 231 | "collapsed": false 232 | }, 233 | "outputs": [ 234 | { 235 | "name": "stdout", 236 | "output_type": "stream", 237 | "text": [ 238 | "\n", 239 | "\n" 240 | ] 241 | } 242 | ], 243 | "source": [ 244 | "print(bz2_opener)\n", 245 | "print(gz2_opener)" 246 | ] 247 | }, 248 | { 249 | "cell_type": "markdown", 250 | "metadata": {}, 251 | "source": [ 252 | "## Namespace Packages" 253 | ] 254 | }, 255 | { 256 | "cell_type": "markdown", 257 | "metadata": {}, 258 | "source": [ 259 | "Namespace packages are used to divide packages into subpackages \n", 260 | "They don't necessarily have a \\__init__.py file \n", 261 | "Consider this file-structure\n", 262 | "```\n", 263 | ".\n", 264 | "├── path1\n", 265 | "│   └── split_farm\n", 266 | "│   └── bovine\n", 267 | "│   ├── common.py\n", 268 | "│   ├── cow.py\n", 269 | "│   ├── __init__.py\n", 270 | "│   ├── ox.py\n", 271 | "│   └── string.py\n", 272 | "└── path2\n", 273 | " └── split_farm\n", 274 | " └── bird\n", 275 | " ├── chicken.py\n", 276 | " ├── __init__.py\n", 277 | " └── turkey.py\n", 278 | "\n", 279 | "```\n", 280 | "Here the farm package is split into two parts part1, part2" 281 | ] 282 | }, 283 | { 284 | "cell_type": "code", 285 | "execution_count": 4, 286 | "metadata": { 287 | "collapsed": true 288 | }, 289 | "outputs": [], 290 | "source": [ 291 | "import sys " 292 | ] 293 | }, 294 | { 295 | "cell_type": "code", 296 | "execution_count": 5, 297 | "metadata": { 298 | "collapsed": true 299 | }, 300 | "outputs": [], 301 | "source": [ 302 | "# Adding path1, path2 to sys.path\n", 303 | "sys.path.extend(['farm/path1/', 'farm/path2/'])" 304 | ] 305 | }, 306 | { 307 | "cell_type": "code", 308 | "execution_count": 6, 309 | "metadata": { 310 | "collapsed": true 311 | }, 312 | "outputs": [], 313 | "source": [ 314 | "# Here python searches for all modules(directories/ files) named split_farm and imports them\n", 315 | "import split_farm" 316 | ] 317 | }, 318 | { 319 | "cell_type": "code", 320 | "execution_count": 7, 321 | "metadata": { 322 | "collapsed": false 323 | }, 324 | "outputs": [ 325 | { 326 | "data": { 327 | "text/plain": [ 328 | "{'In': ['',\n", 329 | " 'from reader.compressed import *',\n", 330 | " 'locals()',\n", 331 | " 'print(bz2_opener)\\nprint(gz2_opener)',\n", 332 | " 'import sys ',\n", 333 | " \"# Adding path1, path2 to sys.path\\nsys.path.extend(['farm/path1/', 'farm/path2/'])\",\n", 334 | " 'import split_farm',\n", 335 | " 'locals()'],\n", 336 | " 'Out': {2: {...}},\n", 337 | " '_': {...},\n", 338 | " '_2': {...},\n", 339 | " '__': '',\n", 340 | " '___': '',\n", 341 | " '__builtin__': ,\n", 342 | " '__builtins__': ,\n", 343 | " '__doc__': 'Automatically created module for IPython interactive environment',\n", 344 | " '__loader__': None,\n", 345 | " '__name__': '__main__',\n", 346 | " '__package__': None,\n", 347 | " '__spec__': None,\n", 348 | " '_dh': ['/home/deen/Code/Python/Python Beyond the Basics'],\n", 349 | " '_i': 'import split_farm',\n", 350 | " '_i1': 'from reader.compressed import *',\n", 351 | " '_i2': 'locals()',\n", 352 | " '_i3': 'print(bz2_opener)\\nprint(gz2_opener)',\n", 353 | " '_i4': 'import sys ',\n", 354 | " '_i5': \"# Adding path1, path2 to sys.path\\nsys.path.extend(['farm/path1/', 'farm/path2/'])\",\n", 355 | " '_i6': 'import split_farm',\n", 356 | " '_i7': 'locals()',\n", 357 | " '_ih': ['',\n", 358 | " 'from reader.compressed import *',\n", 359 | " 'locals()',\n", 360 | " 'print(bz2_opener)\\nprint(gz2_opener)',\n", 361 | " 'import sys ',\n", 362 | " \"# Adding path1, path2 to sys.path\\nsys.path.extend(['farm/path1/', 'farm/path2/'])\",\n", 363 | " 'import split_farm',\n", 364 | " 'locals()'],\n", 365 | " '_ii': \"# Adding path1, path2 to sys.path\\nsys.path.extend(['farm/path1/', 'farm/path2/'])\",\n", 366 | " '_iii': 'import sys ',\n", 367 | " '_oh': {2: {...}},\n", 368 | " '_sh': ,\n", 369 | " 'bz2_opener': ,\n", 370 | " 'exit': ,\n", 371 | " 'get_ipython': >,\n", 372 | " 'gz2_opener': ,\n", 373 | " 'quit': ,\n", 374 | " 'split_farm': ,\n", 375 | " 'sys': }" 376 | ] 377 | }, 378 | "execution_count": 7, 379 | "metadata": {}, 380 | "output_type": "execute_result" 381 | } 382 | ], 383 | "source": [ 384 | "locals()" 385 | ] 386 | }, 387 | { 388 | "cell_type": "code", 389 | "execution_count": 8, 390 | "metadata": { 391 | "collapsed": false 392 | }, 393 | "outputs": [ 394 | { 395 | "name": "stdout", 396 | "output_type": "stream", 397 | "text": [ 398 | "\n" 399 | ] 400 | } 401 | ], 402 | "source": [ 403 | "print(split_farm)" 404 | ] 405 | }, 406 | { 407 | "cell_type": "code", 408 | "execution_count": 10, 409 | "metadata": { 410 | "collapsed": false 411 | }, 412 | "outputs": [ 413 | { 414 | "name": "stdout", 415 | "output_type": "stream", 416 | "text": [ 417 | "_NamespacePath(['farm/path1/split_farm', 'farm/path2/split_farm'])\n" 418 | ] 419 | } 420 | ], 421 | "source": [ 422 | "print(split_farm.__path__) # Both split_farm's are imported" 423 | ] 424 | }, 425 | { 426 | "cell_type": "markdown", 427 | "metadata": {}, 428 | "source": [ 429 | "### Now modules can be imported from an of the split_farm" 430 | ] 431 | }, 432 | { 433 | "cell_type": "code", 434 | "execution_count": 11, 435 | "metadata": { 436 | "collapsed": true 437 | }, 438 | "outputs": [], 439 | "source": [ 440 | "import split_farm.bird\n", 441 | "import split_farm.bovine" 442 | ] 443 | }, 444 | { 445 | "cell_type": "code", 446 | "execution_count": 12, 447 | "metadata": { 448 | "collapsed": false 449 | }, 450 | "outputs": [ 451 | { 452 | "name": "stdout", 453 | "output_type": "stream", 454 | "text": [ 455 | "['farm/path2/split_farm/bird']\n", 456 | "['farm/path1/split_farm/bovine']\n" 457 | ] 458 | } 459 | ], 460 | "source": [ 461 | "print(split_farm.bird.__path__)\n", 462 | "print(split_farm.bovine.__path__)" 463 | ] 464 | } 465 | ], 466 | "metadata": { 467 | "kernelspec": { 468 | "display_name": "Python [conda root]", 469 | "language": "python", 470 | "name": "conda-root-py" 471 | }, 472 | "language_info": { 473 | "codemirror_mode": { 474 | "name": "ipython", 475 | "version": 3 476 | }, 477 | "file_extension": ".py", 478 | "mimetype": "text/x-python", 479 | "name": "python", 480 | "nbconvert_exporter": "python", 481 | "pygments_lexer": "ipython3", 482 | "version": "3.5.2" 483 | } 484 | }, 485 | "nbformat": 4, 486 | "nbformat_minor": 2 487 | } 488 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/004_Executable Directories.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "We can pass directories to python by specifying the \\__main__.py \n", 8 | "These type of directories become executable and can also be zipped to provide similar functionalities\n" 9 | ] 10 | } 11 | ], 12 | "metadata": { 13 | "kernelspec": { 14 | "display_name": "Python [conda root]", 15 | "language": "python", 16 | "name": "conda-root-py" 17 | }, 18 | "language_info": { 19 | "codemirror_mode": { 20 | "name": "ipython", 21 | "version": 3 22 | }, 23 | "file_extension": ".py", 24 | "mimetype": "text/x-python", 25 | "name": "python", 26 | "nbconvert_exporter": "python", 27 | "pygments_lexer": "ipython3", 28 | "version": "3.5.2" 29 | } 30 | }, 31 | "nbformat": 4, 32 | "nbformat_minor": 2 33 | } 34 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/__init__.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/common.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/common.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/cow.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/cow.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/ox.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/ox.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/string.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path1/split_farm/bovine/string.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path2/split_farm/bird/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path2/split_farm/bird/__init__.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path2/split_farm/bird/chicken.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path2/split_farm/bird/chicken.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/farm/path2/split_farm/bird/turkey.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/farm/path2/split_farm/bird/turkey.py -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/folder2_for_001/hello2.py: -------------------------------------------------------------------------------- 1 | def hello(): 2 | print('hello from other folder') 3 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/folder_for_001/hello.py: -------------------------------------------------------------------------------- 1 | def hello(): 2 | print('Hello from folder in path var') 3 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/reader.zip -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader/__main__.py: -------------------------------------------------------------------------------- 1 | ''' 2 | Provides a simple UI to the reader package 3 | 4 | @author: ArchKudo 5 | ''' 6 | import sys 7 | import reader 8 | 9 | try: 10 | file = reader.Reader(sys.argv[1]) 11 | print(file.read()) 12 | file.close() 13 | except: 14 | print('Could not read file') 15 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader/reader/__init__.py: -------------------------------------------------------------------------------- 1 | ''' 2 | Reader package 3 | @author: ArchKudo 4 | ''' 5 | 6 | # Using relative imports 7 | # Similar to reader.reader 8 | from .reader import Reader 9 | 10 | print('Importing pkg...') 11 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader/reader/compressed/__init__.py: -------------------------------------------------------------------------------- 1 | ''' 2 | The compressed subpackage 3 | @author: ArchKudo 4 | ''' 5 | from ..compressed.bzipped import opener as bz2_opener 6 | from ..compressed.gzipped import opener as gz2_opener 7 | 8 | __all__ = ['bz2_opener', 'gz2_opener'] 9 | 10 | print('Importing compressed package...') 11 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader/reader/compressed/bzipped.py: -------------------------------------------------------------------------------- 1 | ''' 2 | bzipped module provides two functionality 3 | * Open bzip2 files 4 | * Compress files to bzip2 5 | 6 | @author: ArchKudo 7 | ''' 8 | import bz2 9 | import sys 10 | 11 | opener = bz2.open 12 | 13 | '''If file is opened as the main file rather than imported''' 14 | if __name__ == '__main__': 15 | file = bz2.open(sys.argv[1], mode='wt') 16 | file.write(''.join(sys.argv[2:])) 17 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader/reader/compressed/gzipped.py: -------------------------------------------------------------------------------- 1 | ''' 2 | gzipped module provides two functionality 3 | * Open gzip2 files 4 | * Compress files to gzip2 5 | 6 | @author: ArchKudo 7 | ''' 8 | import gzip 9 | import sys 10 | 11 | opener = gzip.open 12 | 13 | '''If file is opened as the main file rather than imported''' 14 | if __name__ == '__main__': 15 | f = gzip.open(sys.argv[1], mode='wt') 16 | f.write(''.join(sys.argv[2:])) 17 | f.close() 18 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/reader/reader/reader.py: -------------------------------------------------------------------------------- 1 | ''' 2 | Read from text or compressed files 3 | @author: ArchKudo 4 | ''' 5 | import os 6 | 7 | # Using relative imports 8 | # .compressed is the same as reader.compressed 9 | from .compressed import bzipped, gzipped 10 | 11 | EXT_DICT = {'.bz2': bzipped.opener, 12 | '.gz2': gzipped.opener 13 | } 14 | 15 | 16 | class Reader: 17 | '''Reader Class -- Read contens from text/bzip/gzip files''' 18 | 19 | def __init__(self, filename): 20 | '''Opening a supported file''' 21 | # Get .Extension 22 | extension = os.path.splitext(filename)[1] 23 | 24 | # OPENER is extension.OPENER or equal to open function 25 | opener = EXT_DICT.get(extension, open) 26 | 27 | # Substitutes with bzip2.OPENER/gzip2.OPENER/open 28 | self.file = opener(filename, 'rt') 29 | 30 | def close(self): 31 | ''' Close a file ''' 32 | self.file.close() 33 | 34 | def read(self): 35 | ''' Read a file ''' 36 | return self.file.read() 37 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/test.bz2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/test.bz2 -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/test.file: -------------------------------------------------------------------------------- 1 | Hello from test.file 2 | -------------------------------------------------------------------------------- /002_Organizing_Larger_Programs/test.gz2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/002_Organizing_Larger_Programs/test.gz2 -------------------------------------------------------------------------------- /003_Beyond_Basic_Functions/001_Function Review.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Types of arguments " 8 | ] 9 | }, 10 | { 11 | "cell_type": "markdown", 12 | "metadata": {}, 13 | "source": [ 14 | "### keyword arguments:\n", 15 | "An argument preceded by an identifier (e.g. name=) in a __function call__ or passed as a value in a dictionary preceded by **" 16 | ] 17 | }, 18 | { 19 | "cell_type": "code", 20 | "execution_count": 1, 21 | "metadata": { 22 | "collapsed": false 23 | }, 24 | "outputs": [ 25 | { 26 | "data": { 27 | "text/plain": [ 28 | "(3+5j)" 29 | ] 30 | }, 31 | "execution_count": 1, 32 | "metadata": {}, 33 | "output_type": "execute_result" 34 | } 35 | ], 36 | "source": [ 37 | "complex(real=3, imag=5) " 38 | ] 39 | }, 40 | { 41 | "cell_type": "code", 42 | "execution_count": 2, 43 | "metadata": { 44 | "collapsed": false 45 | }, 46 | "outputs": [ 47 | { 48 | "data": { 49 | "text/plain": [ 50 | "(3+5j)" 51 | ] 52 | }, 53 | "execution_count": 2, 54 | "metadata": {}, 55 | "output_type": "execute_result" 56 | } 57 | ], 58 | "source": [ 59 | "complex(**{'real': 3, 'imag': 5})" 60 | ] 61 | }, 62 | { 63 | "cell_type": "markdown", 64 | "metadata": {}, 65 | "source": [ 66 | "### Positional arguments\n", 67 | "Positional arguments can appear at the beginning of an argument list and/or be passed as elements of an iterable preceded by *" 68 | ] 69 | }, 70 | { 71 | "cell_type": "code", 72 | "execution_count": 3, 73 | "metadata": { 74 | "collapsed": false 75 | }, 76 | "outputs": [ 77 | { 78 | "data": { 79 | "text/plain": [ 80 | "(3+5j)" 81 | ] 82 | }, 83 | "execution_count": 3, 84 | "metadata": {}, 85 | "output_type": "execute_result" 86 | } 87 | ], 88 | "source": [ 89 | "complex(3, 5)" 90 | ] 91 | }, 92 | { 93 | "cell_type": "code", 94 | "execution_count": 4, 95 | "metadata": { 96 | "collapsed": false 97 | }, 98 | "outputs": [ 99 | { 100 | "data": { 101 | "text/plain": [ 102 | "(3+5j)" 103 | ] 104 | }, 105 | "execution_count": 4, 106 | "metadata": {}, 107 | "output_type": "execute_result" 108 | } 109 | ], 110 | "source": [ 111 | "complex(*[3, 5])" 112 | ] 113 | }, 114 | { 115 | "cell_type": "markdown", 116 | "metadata": {}, 117 | "source": [ 118 | "### Function objects are callable objects\n", 119 | "i.e. we can call them" 120 | ] 121 | }, 122 | { 123 | "cell_type": "code", 124 | "execution_count": 5, 125 | "metadata": { 126 | "collapsed": true 127 | }, 128 | "outputs": [], 129 | "source": [ 130 | "import socket" 131 | ] 132 | }, 133 | { 134 | "cell_type": "code", 135 | "execution_count": 6, 136 | "metadata": { 137 | "collapsed": true 138 | }, 139 | "outputs": [], 140 | "source": [ 141 | "def resolve(host):\n", 142 | " return socket.gethostbyname(host)" 143 | ] 144 | }, 145 | { 146 | "cell_type": "code", 147 | "execution_count": 7, 148 | "metadata": { 149 | "collapsed": false 150 | }, 151 | "outputs": [ 152 | { 153 | "name": "stdout", 154 | "output_type": "stream", 155 | "text": [ 156 | "216.58.220.174\n" 157 | ] 158 | } 159 | ], 160 | "source": [ 161 | "print(resolve('google.com'))" 162 | ] 163 | } 164 | ], 165 | "metadata": { 166 | "kernelspec": { 167 | "display_name": "Python [conda root]", 168 | "language": "python", 169 | "name": "conda-root-py" 170 | }, 171 | "language_info": { 172 | "codemirror_mode": { 173 | "name": "ipython", 174 | "version": 3 175 | }, 176 | "file_extension": ".py", 177 | "mimetype": "text/x-python", 178 | "name": "python", 179 | "nbconvert_exporter": "python", 180 | "pygments_lexer": "ipython3", 181 | "version": "3.5.2" 182 | } 183 | }, 184 | "nbformat": 4, 185 | "nbformat_minor": 2 186 | } 187 | -------------------------------------------------------------------------------- /003_Beyond_Basic_Functions/002_Callable Instances.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Creating a cached DNS resolver" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 1, 13 | "metadata": { 14 | "collapsed": true 15 | }, 16 | "outputs": [], 17 | "source": [ 18 | "import socket" 19 | ] 20 | }, 21 | { 22 | "cell_type": "code", 23 | "execution_count": 2, 24 | "metadata": { 25 | "collapsed": true 26 | }, 27 | "outputs": [], 28 | "source": [ 29 | "class Resolver:\n", 30 | "\n", 31 | "\n", 32 | " # Init an empty cache dict\n", 33 | " def __init__(self):\n", 34 | " self._cache = {}\n", 35 | "\n", 36 | "\n", 37 | " # Using class as a callable\n", 38 | " def __call__(self, host):\n", 39 | " if host not in self._cache:\n", 40 | " self._cache[host] = socket.gethostbyname(host)\n", 41 | " return self._cache[host]\n", 42 | "\n", 43 | "\n", 44 | " # Clear cache\n", 45 | " def clear(self):\n", 46 | " self._cache.clear()\n", 47 | "\n", 48 | " \n", 49 | " # Check cache\n", 50 | " def has_host(self, host):\n", 51 | " return host in self._cache\n", 52 | " " 53 | ] 54 | }, 55 | { 56 | "cell_type": "code", 57 | "execution_count": 3, 58 | "metadata": { 59 | "collapsed": false 60 | }, 61 | "outputs": [], 62 | "source": [ 63 | "res = Resolver() # Init" 64 | ] 65 | }, 66 | { 67 | "cell_type": "code", 68 | "execution_count": 4, 69 | "metadata": { 70 | "collapsed": false 71 | }, 72 | "outputs": [ 73 | { 74 | "data": { 75 | "text/plain": [ 76 | "'216.58.220.14'" 77 | ] 78 | }, 79 | "execution_count": 4, 80 | "metadata": {}, 81 | "output_type": "execute_result" 82 | } 83 | ], 84 | "source": [ 85 | "res.__call__('google.com') # Using call method " 86 | ] 87 | }, 88 | { 89 | "cell_type": "code", 90 | "execution_count": 5, 91 | "metadata": { 92 | "collapsed": false 93 | }, 94 | "outputs": [ 95 | { 96 | "data": { 97 | "text/plain": [ 98 | "'74.6.50.24'" 99 | ] 100 | }, 101 | "execution_count": 5, 102 | "metadata": {}, 103 | "output_type": "execute_result" 104 | } 105 | ], 106 | "source": [ 107 | "res('yahoo.co.in') # Shorthand for previous" 108 | ] 109 | }, 110 | { 111 | "cell_type": "code", 112 | "execution_count": 6, 113 | "metadata": { 114 | "collapsed": false 115 | }, 116 | "outputs": [ 117 | { 118 | "data": { 119 | "text/plain": [ 120 | "{'google.com': '216.58.220.14', 'yahoo.co.in': '74.6.50.24'}" 121 | ] 122 | }, 123 | "execution_count": 6, 124 | "metadata": {}, 125 | "output_type": "execute_result" 126 | } 127 | ], 128 | "source": [ 129 | "res._cache" 130 | ] 131 | }, 132 | { 133 | "cell_type": "code", 134 | "execution_count": 7, 135 | "metadata": { 136 | "collapsed": true 137 | }, 138 | "outputs": [], 139 | "source": [ 140 | "res.clear()" 141 | ] 142 | }, 143 | { 144 | "cell_type": "markdown", 145 | "metadata": {}, 146 | "source": [ 147 | "### Timing cache" 148 | ] 149 | }, 150 | { 151 | "cell_type": "code", 152 | "execution_count": 8, 153 | "metadata": { 154 | "collapsed": true 155 | }, 156 | "outputs": [], 157 | "source": [ 158 | "import timeit" 159 | ] 160 | }, 161 | { 162 | "cell_type": "code", 163 | "execution_count": 9, 164 | "metadata": { 165 | "collapsed": false 166 | }, 167 | "outputs": [ 168 | { 169 | "data": { 170 | "text/plain": [ 171 | "0.003053962005651556" 172 | ] 173 | }, 174 | "execution_count": 9, 175 | "metadata": {}, 176 | "output_type": "execute_result" 177 | } 178 | ], 179 | "source": [ 180 | "timeit.timeit(stmt=\"res('yahoo.co.in')\", setup='from __main__ import res', number=1)" 181 | ] 182 | }, 183 | { 184 | "cell_type": "code", 185 | "execution_count": 10, 186 | "metadata": { 187 | "collapsed": false 188 | }, 189 | "outputs": [ 190 | { 191 | "data": { 192 | "text/plain": [ 193 | "7.089009159244597e-06" 194 | ] 195 | }, 196 | "execution_count": 10, 197 | "metadata": {}, 198 | "output_type": "execute_result" 199 | } 200 | ], 201 | "source": [ 202 | "timeit.timeit(stmt=\"res('yahoo.co.in')\", setup='from __main__ import res', number=1)" 203 | ] 204 | }, 205 | { 206 | "cell_type": "code", 207 | "execution_count": 11, 208 | "metadata": { 209 | "collapsed": false 210 | }, 211 | "outputs": [ 212 | { 213 | "name": "stdout", 214 | "output_type": "stream", 215 | "text": [ 216 | "0.000007\n" 217 | ] 218 | } 219 | ], 220 | "source": [ 221 | "## _ saves previous output\n", 222 | "print('{:f}'.format(_))" 223 | ] 224 | }, 225 | { 226 | "cell_type": "markdown", 227 | "metadata": {}, 228 | "source": [ 229 | "## Yet another callable class magic" 230 | ] 231 | }, 232 | { 233 | "cell_type": "code", 234 | "execution_count": 12, 235 | "metadata": { 236 | "collapsed": true 237 | }, 238 | "outputs": [], 239 | "source": [ 240 | "def seq_class(immutable):\n", 241 | " if immutable:\n", 242 | " cls = tuple\n", 243 | " else:\n", 244 | " cls = list\n", 245 | " return cls\n", 246 | "\n", 247 | "name = seq_class(True)" 248 | ] 249 | }, 250 | { 251 | "cell_type": "code", 252 | "execution_count": 13, 253 | "metadata": { 254 | "collapsed": true 255 | }, 256 | "outputs": [], 257 | "source": [ 258 | "# calling the name class\n", 259 | "t = name('Poisson')" 260 | ] 261 | }, 262 | { 263 | "cell_type": "code", 264 | "execution_count": 14, 265 | "metadata": { 266 | "collapsed": false 267 | }, 268 | "outputs": [ 269 | { 270 | "name": "stdout", 271 | "output_type": "stream", 272 | "text": [ 273 | "('P', 'o', 'i', 's', 's', 'o', 'n') \n" 274 | ] 275 | } 276 | ], 277 | "source": [ 278 | "print(t, type(t))" 279 | ] 280 | }, 281 | { 282 | "cell_type": "code", 283 | "execution_count": 15, 284 | "metadata": { 285 | "collapsed": true 286 | }, 287 | "outputs": [], 288 | "source": [ 289 | "# or using conditional expressions\n", 290 | "# x = true_value if condition else false_value\n", 291 | "def seq_class(immutable):\n", 292 | " return tuple if immutable else list\n", 293 | "name = seq_class(False)" 294 | ] 295 | }, 296 | { 297 | "cell_type": "code", 298 | "execution_count": 16, 299 | "metadata": { 300 | "collapsed": true 301 | }, 302 | "outputs": [], 303 | "source": [ 304 | "t = name('legrange')" 305 | ] 306 | }, 307 | { 308 | "cell_type": "code", 309 | "execution_count": 17, 310 | "metadata": { 311 | "collapsed": false 312 | }, 313 | "outputs": [ 314 | { 315 | "name": "stdout", 316 | "output_type": "stream", 317 | "text": [ 318 | "['l', 'e', 'g', 'r', 'a', 'n', 'g', 'e'] \n" 319 | ] 320 | } 321 | ], 322 | "source": [ 323 | "print(t, type(t))" 324 | ] 325 | }, 326 | { 327 | "cell_type": "markdown", 328 | "metadata": {}, 329 | "source": [ 330 | "## Using callable() to check callable objects\n" 331 | ] 332 | }, 333 | { 334 | "cell_type": "code", 335 | "execution_count": 18, 336 | "metadata": { 337 | "collapsed": false 338 | }, 339 | "outputs": [ 340 | { 341 | "data": { 342 | "text/plain": [ 343 | "True" 344 | ] 345 | }, 346 | "execution_count": 18, 347 | "metadata": {}, 348 | "output_type": "execute_result" 349 | } 350 | ], 351 | "source": [ 352 | "callable(Resolver)" 353 | ] 354 | }, 355 | { 356 | "cell_type": "code", 357 | "execution_count": 26, 358 | "metadata": { 359 | "collapsed": false 360 | }, 361 | "outputs": [ 362 | { 363 | "data": { 364 | "text/plain": [ 365 | "True" 366 | ] 367 | }, 368 | "execution_count": 26, 369 | "metadata": {}, 370 | "output_type": "execute_result" 371 | } 372 | ], 373 | "source": [ 374 | "callable(res)" 375 | ] 376 | }, 377 | { 378 | "cell_type": "code", 379 | "execution_count": 21, 380 | "metadata": { 381 | "collapsed": false 382 | }, 383 | "outputs": [ 384 | { 385 | "data": { 386 | "text/plain": [ 387 | "True" 388 | ] 389 | }, 390 | "execution_count": 21, 391 | "metadata": {}, 392 | "output_type": "execute_result" 393 | } 394 | ], 395 | "source": [ 396 | "callable(lambda: None)" 397 | ] 398 | }, 399 | { 400 | "cell_type": "code", 401 | "execution_count": 22, 402 | "metadata": { 403 | "collapsed": false 404 | }, 405 | "outputs": [ 406 | { 407 | "data": { 408 | "text/plain": [ 409 | "False" 410 | ] 411 | }, 412 | "execution_count": 22, 413 | "metadata": {}, 414 | "output_type": "execute_result" 415 | } 416 | ], 417 | "source": [ 418 | "callable('Some string')" 419 | ] 420 | }, 421 | { 422 | "cell_type": "code", 423 | "execution_count": 25, 424 | "metadata": { 425 | "collapsed": false 426 | }, 427 | "outputs": [ 428 | { 429 | "data": { 430 | "text/plain": [ 431 | "True" 432 | ] 433 | }, 434 | "execution_count": 25, 435 | "metadata": {}, 436 | "output_type": "execute_result" 437 | } 438 | ], 439 | "source": [ 440 | "callable(complex)" 441 | ] 442 | }, 443 | { 444 | "cell_type": "code", 445 | "execution_count": 28, 446 | "metadata": { 447 | "collapsed": false 448 | }, 449 | "outputs": [ 450 | { 451 | "data": { 452 | "text/plain": [ 453 | "True" 454 | ] 455 | }, 456 | "execution_count": 28, 457 | "metadata": {}, 458 | "output_type": "execute_result" 459 | } 460 | ], 461 | "source": [ 462 | "callable(res.clear) # Function is callable, however return value may be not" 463 | ] 464 | } 465 | ], 466 | "metadata": { 467 | "kernelspec": { 468 | "display_name": "Python [conda root]", 469 | "language": "python", 470 | "name": "conda-root-py" 471 | }, 472 | "language_info": { 473 | "codemirror_mode": { 474 | "name": "ipython", 475 | "version": 3 476 | }, 477 | "file_extension": ".py", 478 | "mimetype": "text/x-python", 479 | "name": "python", 480 | "nbconvert_exporter": "python", 481 | "pygments_lexer": "ipython3", 482 | "version": "3.5.2" 483 | } 484 | }, 485 | "nbformat": 4, 486 | "nbformat_minor": 2 487 | } 488 | -------------------------------------------------------------------------------- /003_Beyond_Basic_Functions/004_Extended Formal Arguments.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Extended positional arguments" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 1, 13 | "metadata": { 14 | "collapsed": true 15 | }, 16 | "outputs": [], 17 | "source": [ 18 | "# A function to get volume of n-dimensional hypercuboid\n", 19 | "def hypervolume(*lengths):\n", 20 | " v = 1\n", 21 | " for i in lengths:\n", 22 | " v *= i\n", 23 | " return v" 24 | ] 25 | }, 26 | { 27 | "cell_type": "code", 28 | "execution_count": 2, 29 | "metadata": { 30 | "collapsed": false 31 | }, 32 | "outputs": [ 33 | { 34 | "data": { 35 | "text/plain": [ 36 | "24" 37 | ] 38 | }, 39 | "execution_count": 2, 40 | "metadata": {}, 41 | "output_type": "execute_result" 42 | } 43 | ], 44 | "source": [ 45 | "hypervolume(2, 3, 4)" 46 | ] 47 | }, 48 | { 49 | "cell_type": "code", 50 | "execution_count": 3, 51 | "metadata": { 52 | "collapsed": false 53 | }, 54 | "outputs": [ 55 | { 56 | "data": { 57 | "text/plain": [ 58 | "1" 59 | ] 60 | }, 61 | "execution_count": 3, 62 | "metadata": {}, 63 | "output_type": "execute_result" 64 | } 65 | ], 66 | "source": [ 67 | "# However passing 0 arguments produces ugly bugs\n", 68 | "hypervolume()" 69 | ] 70 | }, 71 | { 72 | "cell_type": "code", 73 | "execution_count": 4, 74 | "metadata": { 75 | "collapsed": true 76 | }, 77 | "outputs": [], 78 | "source": [ 79 | "# A better hypervolume\n", 80 | "def hypervolume(dim, *dims):\n", 81 | " v = dim\n", 82 | " for i in dims:\n", 83 | " v *= i\n", 84 | " return v" 85 | ] 86 | }, 87 | { 88 | "cell_type": "code", 89 | "execution_count": 5, 90 | "metadata": { 91 | "collapsed": false 92 | }, 93 | "outputs": [ 94 | { 95 | "name": "stdout", 96 | "output_type": "stream", 97 | "text": [ 98 | "Does not work without passing atleast one args\n" 99 | ] 100 | } 101 | ], 102 | "source": [ 103 | "try:\n", 104 | " hypervolume()\n", 105 | "except:\n", 106 | " print('Does not work without passing atleast one args')" 107 | ] 108 | }, 109 | { 110 | "cell_type": "markdown", 111 | "metadata": {}, 112 | "source": [ 113 | "## Extended keyword arguments" 114 | ] 115 | }, 116 | { 117 | "cell_type": "code", 118 | "execution_count": 6, 119 | "metadata": { 120 | "collapsed": true 121 | }, 122 | "outputs": [], 123 | "source": [ 124 | "def tag_factory(tag, **attributes):\n", 125 | " result = '<' + tag\n", 126 | " for k, v in attributes.items():\n", 127 | " result += ' {k}=\"{v}\"'.format(k=k, v=str(v))\n", 128 | " result += '>'\n", 129 | " return result" 130 | ] 131 | }, 132 | { 133 | "cell_type": "code", 134 | "execution_count": 7, 135 | "metadata": { 136 | "collapsed": false 137 | }, 138 | "outputs": [ 139 | { 140 | "name": "stdout", 141 | "output_type": "stream", 142 | "text": [ 143 | "\"a\n" 144 | ] 145 | } 146 | ], 147 | "source": [ 148 | "print(tag_factory('img', src='kitty.jpg', alt='a kitty'))" 149 | ] 150 | }, 151 | { 152 | "cell_type": "markdown", 153 | "metadata": {}, 154 | "source": [ 155 | "## Extended arguments call syntax" 156 | ] 157 | }, 158 | { 159 | "cell_type": "code", 160 | "execution_count": 8, 161 | "metadata": { 162 | "collapsed": false 163 | }, 164 | "outputs": [], 165 | "source": [ 166 | "def print_tup(item1, item2, *items):\n", 167 | " print('{0}, {1}'.format(item1, type(item1)))\n", 168 | " print('{0}, {1}'.format(item2, type(item2)))\n", 169 | " print('{0}, {1}'.format(items, type(items)))" 170 | ] 171 | }, 172 | { 173 | "cell_type": "code", 174 | "execution_count": 9, 175 | "metadata": { 176 | "collapsed": false 177 | }, 178 | "outputs": [ 179 | { 180 | "name": "stdout", 181 | "output_type": "stream", 182 | "text": [ 183 | "0, \n", 184 | "1, \n", 185 | "(2, 3, 4, 5, 6, 7, 8, 9), \n" 186 | ] 187 | } 188 | ], 189 | "source": [ 190 | "t = tuple(i for i in range(10))\n", 191 | "print_tup(*t)" 192 | ] 193 | }, 194 | { 195 | "cell_type": "code", 196 | "execution_count": 10, 197 | "metadata": { 198 | "collapsed": true 199 | }, 200 | "outputs": [], 201 | "source": [ 202 | "def print_kwargs(i, j, **k):\n", 203 | " print('i=', i)\n", 204 | " print('j=', j)\n", 205 | " print(k)" 206 | ] 207 | }, 208 | { 209 | "cell_type": "code", 210 | "execution_count": 11, 211 | "metadata": { 212 | "collapsed": false 213 | }, 214 | "outputs": [ 215 | { 216 | "name": "stdout", 217 | "output_type": "stream", 218 | "text": [ 219 | "i= a\n", 220 | "j= b\n", 221 | "{'c': 'j'}\n" 222 | ] 223 | } 224 | ], 225 | "source": [ 226 | "k = dict(i='a', j='b', c='j')\n", 227 | "print_kwargs(**k)" 228 | ] 229 | }, 230 | { 231 | "cell_type": "code", 232 | "execution_count": 12, 233 | "metadata": { 234 | "collapsed": false 235 | }, 236 | "outputs": [], 237 | "source": [ 238 | "def trace(f, *args, **kwargs):\n", 239 | " print('args = ', args)\n", 240 | " print('kwargs = ', kwargs)\n", 241 | " result = f(*args, **kwargs)\n", 242 | " print(result)\n" 243 | ] 244 | }, 245 | { 246 | "cell_type": "code", 247 | "execution_count": 13, 248 | "metadata": { 249 | "collapsed": false 250 | }, 251 | "outputs": [ 252 | { 253 | "data": { 254 | "text/plain": [ 255 | "255" 256 | ] 257 | }, 258 | "execution_count": 13, 259 | "metadata": {}, 260 | "output_type": "execute_result" 261 | } 262 | ], 263 | "source": [ 264 | "int('ff', base=16)" 265 | ] 266 | }, 267 | { 268 | "cell_type": "code", 269 | "execution_count": 14, 270 | "metadata": { 271 | "collapsed": false 272 | }, 273 | "outputs": [ 274 | { 275 | "name": "stdout", 276 | "output_type": "stream", 277 | "text": [ 278 | "args = ('ff',)\n", 279 | "kwargs = {'base': 16}\n", 280 | "255\n" 281 | ] 282 | } 283 | ], 284 | "source": [ 285 | "trace(int, 'ff', base=16)" 286 | ] 287 | }, 288 | { 289 | "cell_type": "code", 290 | "execution_count": 15, 291 | "metadata": { 292 | "collapsed": true 293 | }, 294 | "outputs": [], 295 | "source": [ 296 | "from random import randint" 297 | ] 298 | }, 299 | { 300 | "cell_type": "code", 301 | "execution_count": 17, 302 | "metadata": { 303 | "collapsed": false 304 | }, 305 | "outputs": [], 306 | "source": [ 307 | "t = [[randint(10 * i, 10 * i + 10) for x in range(10)] for i in range(3)]" 308 | ] 309 | }, 310 | { 311 | "cell_type": "code", 312 | "execution_count": 18, 313 | "metadata": { 314 | "collapsed": false 315 | }, 316 | "outputs": [], 317 | "source": [ 318 | "from pprint import pprint as pp" 319 | ] 320 | }, 321 | { 322 | "cell_type": "code", 323 | "execution_count": 19, 324 | "metadata": { 325 | "collapsed": false 326 | }, 327 | "outputs": [ 328 | { 329 | "name": "stdout", 330 | "output_type": "stream", 331 | "text": [ 332 | "[[5, 4, 1, 3, 2, 0, 0, 6, 8, 10],\n", 333 | " [14, 18, 17, 20, 15, 18, 18, 12, 19, 18],\n", 334 | " [25, 22, 22, 27, 24, 20, 21, 22, 21, 28]]\n" 335 | ] 336 | } 337 | ], 338 | "source": [ 339 | "pp(mat)" 340 | ] 341 | }, 342 | { 343 | "cell_type": "code", 344 | "execution_count": 20, 345 | "metadata": { 346 | "collapsed": false 347 | }, 348 | "outputs": [ 349 | { 350 | "name": "stdout", 351 | "output_type": "stream", 352 | "text": [ 353 | "(5, 14, 25)\n", 354 | "(4, 18, 22)\n", 355 | "(1, 17, 22)\n", 356 | "(3, 20, 27)\n", 357 | "(2, 15, 24)\n", 358 | "(0, 18, 20)\n", 359 | "(0, 18, 21)\n", 360 | "(6, 12, 22)\n", 361 | "(8, 19, 21)\n", 362 | "(10, 18, 28)\n" 363 | ] 364 | } 365 | ], 366 | "source": [ 367 | "for item in zip(mat[0], mat[1], mat[2]):\n", 368 | " pp(item)" 369 | ] 370 | }, 371 | { 372 | "cell_type": "code", 373 | "execution_count": 21, 374 | "metadata": { 375 | "collapsed": false 376 | }, 377 | "outputs": [ 378 | { 379 | "name": "stdout", 380 | "output_type": "stream", 381 | "text": [ 382 | "(5, 14, 25)\n", 383 | "(4, 18, 22)\n", 384 | "(1, 17, 22)\n", 385 | "(3, 20, 27)\n", 386 | "(2, 15, 24)\n", 387 | "(0, 18, 20)\n", 388 | "(0, 18, 21)\n", 389 | "(6, 12, 22)\n", 390 | "(8, 19, 21)\n", 391 | "(10, 18, 28)\n" 392 | ] 393 | } 394 | ], 395 | "source": [ 396 | "for item in zip(*mat):\n", 397 | " pp(item)" 398 | ] 399 | }, 400 | { 401 | "cell_type": "code", 402 | "execution_count": 22, 403 | "metadata": { 404 | "collapsed": false, 405 | "scrolled": true 406 | }, 407 | "outputs": [ 408 | { 409 | "name": "stdout", 410 | "output_type": "stream", 411 | "text": [ 412 | "[[5, 4, 1, 3, 2, 0, 0, 6, 8, 10],\n", 413 | " [14, 18, 17, 20, 15, 18, 18, 12, 19, 18],\n", 414 | " [25, 22, 22, 27, 24, 20, 21, 22, 21, 28]]\n", 415 | "[(5, 14, 25),\n", 416 | " (4, 18, 22),\n", 417 | " (1, 17, 22),\n", 418 | " (3, 20, 27),\n", 419 | " (2, 15, 24),\n", 420 | " (0, 18, 20),\n", 421 | " (0, 18, 21),\n", 422 | " (6, 12, 22),\n", 423 | " (8, 19, 21),\n", 424 | " (10, 18, 28)]\n" 425 | ] 426 | } 427 | ], 428 | "source": [ 429 | "# Transposed\n", 430 | "transposed = list(zip(*mat))\n", 431 | "pp(mat)\n", 432 | "pp(transposed)" 433 | ] 434 | }, 435 | { 436 | "cell_type": "code", 437 | "execution_count": null, 438 | "metadata": { 439 | "collapsed": true 440 | }, 441 | "outputs": [], 442 | "source": [] 443 | } 444 | ], 445 | "metadata": { 446 | "kernelspec": { 447 | "display_name": "Python [conda root]", 448 | "language": "python", 449 | "name": "conda-root-py" 450 | }, 451 | "language_info": { 452 | "codemirror_mode": { 453 | "name": "ipython", 454 | "version": 3 455 | }, 456 | "file_extension": ".py", 457 | "mimetype": "text/x-python", 458 | "name": "python", 459 | "nbconvert_exporter": "python", 460 | "pygments_lexer": "ipython3", 461 | "version": "3.5.2" 462 | } 463 | }, 464 | "nbformat": 4, 465 | "nbformat_minor": 2 466 | } 467 | -------------------------------------------------------------------------------- /003_Beyond_Basic_Functions/lamda_diff.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/003_Beyond_Basic_Functions/lamda_diff.jpg -------------------------------------------------------------------------------- /004_Closures_and_Decorators/001_LEGB Scope Rules.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Functions can be defined inside other functions" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 1, 13 | "metadata": { 14 | "collapsed": false 15 | }, 16 | "outputs": [ 17 | { 18 | "name": "stdout", 19 | "output_type": "stream", 20 | "text": [ 21 | "3\n" 22 | ] 23 | } 24 | ], 25 | "source": [ 26 | "# A simple function\n", 27 | "def func():\n", 28 | " x = 1\n", 29 | " y = 2\n", 30 | " return x + y\n", 31 | "print(func())" 32 | ] 33 | }, 34 | { 35 | "cell_type": "code", 36 | "execution_count": 12, 37 | "metadata": { 38 | "collapsed": false 39 | }, 40 | "outputs": [ 41 | { 42 | "name": "stdout", 43 | "output_type": "stream", 44 | "text": [ 45 | "hello, world!\n", 46 | "local_func() not defined\n" 47 | ] 48 | } 49 | ], 50 | "source": [ 51 | "# A local function inside a function\n", 52 | "def func():\n", 53 | " def local_func():\n", 54 | " return 'hello, world!'\n", 55 | " return local_func()\n", 56 | "\n", 57 | "print(func())\n", 58 | "try:\n", 59 | " print(local_func())\n", 60 | "except:\n", 61 | " print('local_func() not defined')" 62 | ] 63 | }, 64 | { 65 | "cell_type": "code", 66 | "execution_count": 30, 67 | "metadata": { 68 | "collapsed": true 69 | }, 70 | "outputs": [], 71 | "source": [ 72 | "# Another example to sort a string\n", 73 | "store = [] # To store instances of \n", 74 | "def sort(string):\n", 75 | " def last_letter(s):\n", 76 | " return s[-1]\n", 77 | " store.append(last_letter)\n", 78 | " return sorted(string, key=last_letter)\n" 79 | ] 80 | }, 81 | { 82 | "cell_type": "code", 83 | "execution_count": 32, 84 | "metadata": { 85 | "collapsed": false 86 | }, 87 | "outputs": [ 88 | { 89 | "name": "stdout", 90 | "output_type": "stream", 91 | "text": [ 92 | "['ba', 'ab', 'db', 'cd']\n", 93 | "[.last_letter at 0x7fbbbc29db70>, .last_letter at 0x7fbbbc299268>]\n" 94 | ] 95 | } 96 | ], 97 | "source": [ 98 | "print(sort(['ab', 'ba', 'cd', 'db']))\n", 99 | "print(store) # A new function is created everytime def is executed (here it is run two times)" 100 | ] 101 | }, 102 | { 103 | "cell_type": "markdown", 104 | "metadata": {}, 105 | "source": [ 106 | "## The LEGB rule\n", 107 | "\n", 108 | "1. Local \n", 109 | "2. Enclosed\n", 110 | "3. Global\n", 111 | "4. Built-in\n", 112 | "\n" 113 | ] 114 | }, 115 | { 116 | "cell_type": "code", 117 | "execution_count": 11, 118 | "metadata": { 119 | "collapsed": false 120 | }, 121 | "outputs": [ 122 | { 123 | "name": "stdout", 124 | "output_type": "stream", 125 | "text": [ 126 | "Hi from local_func 102 103 104\n", 127 | "Hi from func 69 70 71\n", 128 | "Hi from __main__ 42 43 44\n" 129 | ] 130 | } 131 | ], 132 | "source": [ 133 | "(x, y, z) = 42, 43, 44 # Global scope\n", 134 | "def func():\n", 135 | " (x, y, z) = 69, 70, 71 # Enclosed scope for local_func(), local scope for func()\n", 136 | " def local_func():\n", 137 | " (x, y, z) = 102, 103, 104 # Local scope\n", 138 | " print('Hi from', local_func.__name__, x, y, z)\n", 139 | " local_func()\n", 140 | " print('Hi from', func.__name__, x, y, z)\n", 141 | "func()\n", 142 | "print('Hi from', __name__, x, y, z)" 143 | ] 144 | }, 145 | { 146 | "cell_type": "markdown", 147 | "metadata": {}, 148 | "source": [ 149 | "### However local functions don't change the variables of the enclosing / global scope\n", 150 | "In the following code every function creates its own __message__ variable" 151 | ] 152 | }, 153 | { 154 | "cell_type": "code", 155 | "execution_count": 4, 156 | "metadata": { 157 | "collapsed": false 158 | }, 159 | "outputs": [ 160 | { 161 | "name": "stdout", 162 | "output_type": "stream", 163 | "text": [ 164 | "local\n", 165 | "enclosing\n", 166 | "global\n" 167 | ] 168 | } 169 | ], 170 | "source": [ 171 | "message = 'global'\n", 172 | "\n", 173 | "\n", 174 | "def enclosing():\n", 175 | " message = 'enclosing'\n", 176 | " def local():\n", 177 | " message = 'local'\n", 178 | " print(message)\n", 179 | " local()\n", 180 | " print(message)\n", 181 | " \n", 182 | "\n", 183 | "enclosing()\n", 184 | "print(message)" 185 | ] 186 | }, 187 | { 188 | "cell_type": "markdown", 189 | "metadata": {}, 190 | "source": [ 191 | "### To change global variables we could use the global keyword" 192 | ] 193 | }, 194 | { 195 | "cell_type": "code", 196 | "execution_count": 6, 197 | "metadata": { 198 | "collapsed": false 199 | }, 200 | "outputs": [ 201 | { 202 | "name": "stdout", 203 | "output_type": "stream", 204 | "text": [ 205 | "local\n", 206 | "enclosing\n", 207 | "local\n" 208 | ] 209 | } 210 | ], 211 | "source": [ 212 | "message = 'global'\n", 213 | "\n", 214 | "\n", 215 | "def enclosing():\n", 216 | " message = 'enclosing'\n", 217 | " def local():\n", 218 | " global message\n", 219 | " message = 'local'\n", 220 | " print(message) # Changes message from 'global' -> 'local'\n", 221 | " local()\n", 222 | " print(message)\n", 223 | " \n", 224 | "\n", 225 | "enclosing()\n", 226 | "print(message)" 227 | ] 228 | }, 229 | { 230 | "cell_type": "markdown", 231 | "metadata": {}, 232 | "source": [ 233 | "### To change enclosing variables we use nonlocal keyword" 234 | ] 235 | }, 236 | { 237 | "cell_type": "code", 238 | "execution_count": 7, 239 | "metadata": { 240 | "collapsed": false 241 | }, 242 | "outputs": [ 243 | { 244 | "name": "stdout", 245 | "output_type": "stream", 246 | "text": [ 247 | "local\n", 248 | "local\n", 249 | "global\n" 250 | ] 251 | } 252 | ], 253 | "source": [ 254 | "message = 'global'\n", 255 | "\n", 256 | "\n", 257 | "def enclosing():\n", 258 | " message = 'enclosing'\n", 259 | " def local():\n", 260 | " nonlocal message\n", 261 | " message = 'local'\n", 262 | " print(message) # Changes message from 'enclosing' -> 'local'\n", 263 | " local()\n", 264 | " print(message)\n", 265 | " \n", 266 | "\n", 267 | "enclosing()\n", 268 | "print(message)" 269 | ] 270 | }, 271 | { 272 | "cell_type": "markdown", 273 | "metadata": {}, 274 | "source": [ 275 | "### A more practical example of when to use nonlocal" 276 | ] 277 | }, 278 | { 279 | "cell_type": "code", 280 | "execution_count": 8, 281 | "metadata": { 282 | "collapsed": true 283 | }, 284 | "outputs": [], 285 | "source": [ 286 | "import time" 287 | ] 288 | }, 289 | { 290 | "cell_type": "code", 291 | "execution_count": 23, 292 | "metadata": { 293 | "collapsed": true 294 | }, 295 | "outputs": [], 296 | "source": [ 297 | "def make_timer():\n", 298 | " last_called = None\n", 299 | " \n", 300 | " def elapsed():\n", 301 | " nonlocal last_called\n", 302 | " now = time.time()\n", 303 | " \n", 304 | " if last_called is None:\n", 305 | " last_called = now\n", 306 | " return None\n", 307 | " \n", 308 | " result = now - last_called\n", 309 | " last_called = now\n", 310 | " return result\n", 311 | " \n", 312 | " return elapsed" 313 | ] 314 | }, 315 | { 316 | "cell_type": "code", 317 | "execution_count": 24, 318 | "metadata": { 319 | "collapsed": true 320 | }, 321 | "outputs": [], 322 | "source": [ 323 | "new_timer = make_timer()" 324 | ] 325 | }, 326 | { 327 | "cell_type": "code", 328 | "execution_count": 25, 329 | "metadata": { 330 | "collapsed": true 331 | }, 332 | "outputs": [], 333 | "source": [ 334 | "new_timer()" 335 | ] 336 | }, 337 | { 338 | "cell_type": "code", 339 | "execution_count": 26, 340 | "metadata": { 341 | "collapsed": false 342 | }, 343 | "outputs": [ 344 | { 345 | "data": { 346 | "text/plain": [ 347 | "1.1587612628936768" 348 | ] 349 | }, 350 | "execution_count": 26, 351 | "metadata": {}, 352 | "output_type": "execute_result" 353 | } 354 | ], 355 | "source": [ 356 | "new_timer()" 357 | ] 358 | }, 359 | { 360 | "cell_type": "code", 361 | "execution_count": 27, 362 | "metadata": { 363 | "collapsed": false 364 | }, 365 | "outputs": [ 366 | { 367 | "data": { 368 | "text/plain": [ 369 | "1.820242166519165" 370 | ] 371 | }, 372 | "execution_count": 27, 373 | "metadata": {}, 374 | "output_type": "execute_result" 375 | } 376 | ], 377 | "source": [ 378 | "new_timer()" 379 | ] 380 | }, 381 | { 382 | "cell_type": "markdown", 383 | "metadata": {}, 384 | "source": [ 385 | "All new timers are independent" 386 | ] 387 | }, 388 | { 389 | "cell_type": "code", 390 | "execution_count": 28, 391 | "metadata": { 392 | "collapsed": true 393 | }, 394 | "outputs": [], 395 | "source": [ 396 | "new_timer2 = make_timer()" 397 | ] 398 | }, 399 | { 400 | "cell_type": "code", 401 | "execution_count": 29, 402 | "metadata": { 403 | "collapsed": true 404 | }, 405 | "outputs": [], 406 | "source": [ 407 | "new_timer2()" 408 | ] 409 | }, 410 | { 411 | "cell_type": "code", 412 | "execution_count": 30, 413 | "metadata": { 414 | "collapsed": false 415 | }, 416 | "outputs": [ 417 | { 418 | "data": { 419 | "text/plain": [ 420 | "0.6697626113891602" 421 | ] 422 | }, 423 | "execution_count": 30, 424 | "metadata": {}, 425 | "output_type": "execute_result" 426 | } 427 | ], 428 | "source": [ 429 | "new_timer2()" 430 | ] 431 | }, 432 | { 433 | "cell_type": "code", 434 | "execution_count": 31, 435 | "metadata": { 436 | "collapsed": false 437 | }, 438 | "outputs": [ 439 | { 440 | "data": { 441 | "text/plain": [ 442 | "5.053479909896851" 443 | ] 444 | }, 445 | "execution_count": 31, 446 | "metadata": {}, 447 | "output_type": "execute_result" 448 | } 449 | ], 450 | "source": [ 451 | "new_timer() " 452 | ] 453 | }, 454 | { 455 | "cell_type": "code", 456 | "execution_count": null, 457 | "metadata": { 458 | "collapsed": true 459 | }, 460 | "outputs": [], 461 | "source": [] 462 | } 463 | ], 464 | "metadata": { 465 | "kernelspec": { 466 | "display_name": "Python [conda root]", 467 | "language": "python", 468 | "name": "conda-root-py" 469 | }, 470 | "language_info": { 471 | "codemirror_mode": { 472 | "name": "ipython", 473 | "version": 3 474 | }, 475 | "file_extension": ".py", 476 | "mimetype": "text/x-python", 477 | "name": "python", 478 | "nbconvert_exporter": "python", 479 | "pygments_lexer": "ipython3", 480 | "version": "3.5.2" 481 | } 482 | }, 483 | "nbformat": 4, 484 | "nbformat_minor": 2 485 | } 486 | -------------------------------------------------------------------------------- /004_Closures_and_Decorators/002_Closures and Function Factories.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Closures\n", 8 | "A function which remembers environment in which it was created" 9 | ] 10 | }, 11 | { 12 | "cell_type": "code", 13 | "execution_count": 24, 14 | "metadata": { 15 | "collapsed": true 16 | }, 17 | "outputs": [], 18 | "source": [ 19 | "def enclosing():\n", 20 | " x = 'closed over from enclosing()..'\n", 21 | " y = 'Am I included too?'\n", 22 | " def local_func():\n", 23 | " print(x)\n", 24 | " # print(y)\n", 25 | " return local_func" 26 | ] 27 | }, 28 | { 29 | "cell_type": "code", 30 | "execution_count": 25, 31 | "metadata": { 32 | "collapsed": false 33 | }, 34 | "outputs": [ 35 | { 36 | "data": { 37 | "text/plain": [ 38 | ".local_func>" 39 | ] 40 | }, 41 | "execution_count": 25, 42 | "metadata": {}, 43 | "output_type": "execute_result" 44 | } 45 | ], 46 | "source": [ 47 | "enclosing() # Returns local_func" 48 | ] 49 | }, 50 | { 51 | "cell_type": "code", 52 | "execution_count": 26, 53 | "metadata": { 54 | "collapsed": true 55 | }, 56 | "outputs": [], 57 | "source": [ 58 | "lf = enclosing() # Set lf to return value of enclosing() i.e is local_func" 59 | ] 60 | }, 61 | { 62 | "cell_type": "markdown", 63 | "metadata": {}, 64 | "source": [ 65 | "Here __x__'s value is retained even after __enclosing()__ function exited" 66 | ] 67 | }, 68 | { 69 | "cell_type": "code", 70 | "execution_count": 27, 71 | "metadata": { 72 | "collapsed": false 73 | }, 74 | "outputs": [ 75 | { 76 | "name": "stdout", 77 | "output_type": "stream", 78 | "text": [ 79 | "closed over from enclosing()..\n" 80 | ] 81 | } 82 | ], 83 | "source": [ 84 | "lf()" 85 | ] 86 | }, 87 | { 88 | "cell_type": "code", 89 | "execution_count": 28, 90 | "metadata": { 91 | "collapsed": false 92 | }, 93 | "outputs": [ 94 | { 95 | "data": { 96 | "text/plain": [ 97 | "(,)" 98 | ] 99 | }, 100 | "execution_count": 28, 101 | "metadata": {}, 102 | "output_type": "execute_result" 103 | } 104 | ], 105 | "source": [ 106 | "lf.__closure__ # Prints all the environment variables in it was created" 107 | ] 108 | }, 109 | { 110 | "cell_type": "markdown", 111 | "metadata": {}, 112 | "source": [ 113 | "## Function Factory\n", 114 | "Function used to generate other functions" 115 | ] 116 | }, 117 | { 118 | "cell_type": "code", 119 | "execution_count": 33, 120 | "metadata": { 121 | "collapsed": true 122 | }, 123 | "outputs": [], 124 | "source": [ 125 | "# Create a function to generate functions which raise to a certain power\n", 126 | "def raise_factory(exp):\n", 127 | " def raise_to_exp(x):\n", 128 | " return pow(x, exp)\n", 129 | " return raise_to_exp" 130 | ] 131 | }, 132 | { 133 | "cell_type": "code", 134 | "execution_count": 38, 135 | "metadata": { 136 | "collapsed": false 137 | }, 138 | "outputs": [ 139 | { 140 | "name": "stdout", 141 | "output_type": "stream", 142 | "text": [ 143 | "144\n", 144 | "(,)\n" 145 | ] 146 | } 147 | ], 148 | "source": [ 149 | "square = raise_factory(2)\n", 150 | "print(square(12))\n", 151 | "print(square.__closure__) # Stores the exp int" 152 | ] 153 | }, 154 | { 155 | "cell_type": "code", 156 | "execution_count": 37, 157 | "metadata": { 158 | "collapsed": false 159 | }, 160 | "outputs": [ 161 | { 162 | "name": "stdout", 163 | "output_type": "stream", 164 | "text": [ 165 | "1728\n", 166 | "(,)\n" 167 | ] 168 | } 169 | ], 170 | "source": [ 171 | "cube = raise_factory(3)\n", 172 | "print(cube(12))\n", 173 | "print(cube.__closure__)" 174 | ] 175 | } 176 | ], 177 | "metadata": { 178 | "kernelspec": { 179 | "display_name": "Python [conda root]", 180 | "language": "python", 181 | "name": "conda-root-py" 182 | }, 183 | "language_info": { 184 | "codemirror_mode": { 185 | "name": "ipython", 186 | "version": 3 187 | }, 188 | "file_extension": ".py", 189 | "mimetype": "text/x-python", 190 | "name": "python", 191 | "nbconvert_exporter": "python", 192 | "pygments_lexer": "ipython3", 193 | "version": "3.5.2" 194 | } 195 | }, 196 | "nbformat": 4, 197 | "nbformat_minor": 2 198 | } 199 | -------------------------------------------------------------------------------- /004_Closures_and_Decorators/003_Decorators.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Creating a function decorator " 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 2, 13 | "metadata": { 14 | "collapsed": true 15 | }, 16 | "outputs": [], 17 | "source": [ 18 | "def escape_unicode(f):\n", 19 | " def wrap(*args, **kwargs):\n", 20 | " x = f(*args, **kwargs)\n", 21 | " return ascii(x)\n", 22 | " return wrap" 23 | ] 24 | }, 25 | { 26 | "cell_type": "markdown", 27 | "metadata": {}, 28 | "source": [ 29 | "## Using the decorator" 30 | ] 31 | }, 32 | { 33 | "cell_type": "code", 34 | "execution_count": 3, 35 | "metadata": { 36 | "collapsed": false 37 | }, 38 | "outputs": [ 39 | { 40 | "name": "stdout", 41 | "output_type": "stream", 42 | "text": [ 43 | "₹₹°\n" 44 | ] 45 | } 46 | ], 47 | "source": [ 48 | "def rupee():\n", 49 | " return '₹₹°'\n", 50 | "\n", 51 | "print(rupee())" 52 | ] 53 | }, 54 | { 55 | "cell_type": "code", 56 | "execution_count": 6, 57 | "metadata": { 58 | "collapsed": false 59 | }, 60 | "outputs": [ 61 | { 62 | "name": "stdout", 63 | "output_type": "stream", 64 | "text": [ 65 | "'\\u20b9\\u20b9\\xb0'\n" 66 | ] 67 | } 68 | ], 69 | "source": [ 70 | "@escape_unicode\n", 71 | "def rupee():\n", 72 | " return '₹₹°'\n", 73 | "\n", 74 | "print(rupee())" 75 | ] 76 | }, 77 | { 78 | "cell_type": "markdown", 79 | "metadata": {}, 80 | "source": [ 81 | "## Creating class decorators\n", 82 | "A decorator is a callable that takes in an callable as an argument and returns a callable. \n", 83 | "Therefore to be available to be used with class it must define \\__call\\__ method" 84 | ] 85 | }, 86 | { 87 | "cell_type": "code", 88 | "execution_count": 12, 89 | "metadata": { 90 | "collapsed": true 91 | }, 92 | "outputs": [], 93 | "source": [ 94 | "class CallCount:\n", 95 | " def __init__(self, f):\n", 96 | " self.f = f\n", 97 | " self.count = 0\n", 98 | " \n", 99 | " def __call__(self, *args, **kwargs):\n", 100 | " self.count += 1\n", 101 | " return self.f(*args, **kwargs)" 102 | ] 103 | }, 104 | { 105 | "cell_type": "code", 106 | "execution_count": 13, 107 | "metadata": { 108 | "collapsed": true 109 | }, 110 | "outputs": [], 111 | "source": [ 112 | "@CallCount\n", 113 | "def hello(name):\n", 114 | " print('Hello ', name, '!')" 115 | ] 116 | }, 117 | { 118 | "cell_type": "code", 119 | "execution_count": 14, 120 | "metadata": { 121 | "collapsed": false 122 | }, 123 | "outputs": [ 124 | { 125 | "name": "stdout", 126 | "output_type": "stream", 127 | "text": [ 128 | "Hello hiro !\n" 129 | ] 130 | } 131 | ], 132 | "source": [ 133 | "hello('hiro')" 134 | ] 135 | }, 136 | { 137 | "cell_type": "code", 138 | "execution_count": 15, 139 | "metadata": { 140 | "collapsed": false 141 | }, 142 | "outputs": [ 143 | { 144 | "name": "stdout", 145 | "output_type": "stream", 146 | "text": [ 147 | "Hello tatsuya !\n" 148 | ] 149 | } 150 | ], 151 | "source": [ 152 | "hello('tatsuya')" 153 | ] 154 | }, 155 | { 156 | "cell_type": "code", 157 | "execution_count": 16, 158 | "metadata": { 159 | "collapsed": false 160 | }, 161 | "outputs": [ 162 | { 163 | "name": "stdout", 164 | "output_type": "stream", 165 | "text": [ 166 | "Hello aang !\n" 167 | ] 168 | } 169 | ], 170 | "source": [ 171 | "hello('aang')" 172 | ] 173 | }, 174 | { 175 | "cell_type": "code", 176 | "execution_count": 17, 177 | "metadata": { 178 | "collapsed": false 179 | }, 180 | "outputs": [ 181 | { 182 | "data": { 183 | "text/plain": [ 184 | "3" 185 | ] 186 | }, 187 | "execution_count": 17, 188 | "metadata": {}, 189 | "output_type": "execute_result" 190 | } 191 | ], 192 | "source": [ 193 | "hello.count" 194 | ] 195 | }, 196 | { 197 | "cell_type": "code", 198 | "execution_count": 18, 199 | "metadata": { 200 | "collapsed": false 201 | }, 202 | "outputs": [ 203 | { 204 | "data": { 205 | "text/plain": [ 206 | "__main__.CallCount" 207 | ] 208 | }, 209 | "execution_count": 18, 210 | "metadata": {}, 211 | "output_type": "execute_result" 212 | } 213 | ], 214 | "source": [ 215 | "type(hello)" 216 | ] 217 | }, 218 | { 219 | "cell_type": "markdown", 220 | "metadata": {}, 221 | "source": [ 222 | "## Class instances as decorators" 223 | ] 224 | }, 225 | { 226 | "cell_type": "code", 227 | "execution_count": 19, 228 | "metadata": { 229 | "collapsed": true 230 | }, 231 | "outputs": [], 232 | "source": [ 233 | "class Trace:\n", 234 | " def __init__(self):\n", 235 | " self.enabled = True\n", 236 | " \n", 237 | " def __call__(self, f):\n", 238 | " def wrap(*args, **kwargs):\n", 239 | " if self.enabled:\n", 240 | " print('Calling {}'.format(f))\n", 241 | " return f(*args, **kwargs)\n", 242 | " return wrap" 243 | ] 244 | }, 245 | { 246 | "cell_type": "code", 247 | "execution_count": 26, 248 | "metadata": { 249 | "collapsed": true 250 | }, 251 | "outputs": [], 252 | "source": [ 253 | "tracer = Trace()\n", 254 | "\n", 255 | "@tracer\n", 256 | "def rotate_list(l):\n", 257 | " return l[1:] + [l[0]]" 258 | ] 259 | }, 260 | { 261 | "cell_type": "code", 262 | "execution_count": 27, 263 | "metadata": { 264 | "collapsed": false 265 | }, 266 | "outputs": [ 267 | { 268 | "name": "stdout", 269 | "output_type": "stream", 270 | "text": [ 271 | "Calling \n" 272 | ] 273 | }, 274 | { 275 | "data": { 276 | "text/plain": [ 277 | "[2, 3, 1]" 278 | ] 279 | }, 280 | "execution_count": 27, 281 | "metadata": {}, 282 | "output_type": "execute_result" 283 | } 284 | ], 285 | "source": [ 286 | "rotate_list([1, 2, 3])" 287 | ] 288 | }, 289 | { 290 | "cell_type": "code", 291 | "execution_count": 28, 292 | "metadata": { 293 | "collapsed": false 294 | }, 295 | "outputs": [ 296 | { 297 | "name": "stdout", 298 | "output_type": "stream", 299 | "text": [ 300 | "Calling \n" 301 | ] 302 | }, 303 | { 304 | "data": { 305 | "text/plain": [ 306 | "[5, 6, 4]" 307 | ] 308 | }, 309 | "execution_count": 28, 310 | "metadata": {}, 311 | "output_type": "execute_result" 312 | } 313 | ], 314 | "source": [ 315 | "rotate_list([4, 5 ,6])" 316 | ] 317 | }, 318 | { 319 | "cell_type": "code", 320 | "execution_count": 31, 321 | "metadata": { 322 | "collapsed": true 323 | }, 324 | "outputs": [], 325 | "source": [ 326 | "tracer.enabled = False" 327 | ] 328 | }, 329 | { 330 | "cell_type": "code", 331 | "execution_count": 35, 332 | "metadata": { 333 | "collapsed": false 334 | }, 335 | "outputs": [ 336 | { 337 | "data": { 338 | "text/plain": [ 339 | "[4, 1, 3]" 340 | ] 341 | }, 342 | "execution_count": 35, 343 | "metadata": {}, 344 | "output_type": "execute_result" 345 | } 346 | ], 347 | "source": [ 348 | "rotate_list([3, 4, 1])" 349 | ] 350 | }, 351 | { 352 | "cell_type": "markdown", 353 | "metadata": {}, 354 | "source": [ 355 | "## Using multiple decorators on functions" 356 | ] 357 | }, 358 | { 359 | "cell_type": "code", 360 | "execution_count": 38, 361 | "metadata": { 362 | "collapsed": true 363 | }, 364 | "outputs": [], 365 | "source": [ 366 | "@tracer\n", 367 | "@escape_unicode\n", 368 | "def rupee_maker(money):\n", 369 | " return '₹' + str(money)" 370 | ] 371 | }, 372 | { 373 | "cell_type": "code", 374 | "execution_count": 39, 375 | "metadata": { 376 | "collapsed": false 377 | }, 378 | "outputs": [ 379 | { 380 | "name": "stdout", 381 | "output_type": "stream", 382 | "text": [ 383 | "Calling .wrap at 0x7f8268770510>\n" 384 | ] 385 | }, 386 | { 387 | "data": { 388 | "text/plain": [ 389 | "\"'\\\\u20b912'\"" 390 | ] 391 | }, 392 | "execution_count": 39, 393 | "metadata": {}, 394 | "output_type": "execute_result" 395 | } 396 | ], 397 | "source": [ 398 | "rupee_maker(12)" 399 | ] 400 | }, 401 | { 402 | "cell_type": "code", 403 | "execution_count": 41, 404 | "metadata": { 405 | "collapsed": false 406 | }, 407 | "outputs": [ 408 | { 409 | "name": "stdout", 410 | "output_type": "stream", 411 | "text": [ 412 | "Calling .wrap at 0x7f8268770510>\n" 413 | ] 414 | }, 415 | { 416 | "data": { 417 | "text/plain": [ 418 | "\"'\\\\u20b923'\"" 419 | ] 420 | }, 421 | "execution_count": 41, 422 | "metadata": {}, 423 | "output_type": "execute_result" 424 | } 425 | ], 426 | "source": [ 427 | "rupee_maker(23)" 428 | ] 429 | }, 430 | { 431 | "cell_type": "markdown", 432 | "metadata": {}, 433 | "source": [ 434 | "## Using decorators on class" 435 | ] 436 | }, 437 | { 438 | "cell_type": "code", 439 | "execution_count": 49, 440 | "metadata": { 441 | "collapsed": false 442 | }, 443 | "outputs": [], 444 | "source": [ 445 | "class MoneyMaker:\n", 446 | " def __init__(self, prefix):\n", 447 | " self.prefix = prefix\n", 448 | " @tracer\n", 449 | " def make_money(self, value):\n", 450 | " return self.prefix + str(value)" 451 | ] 452 | }, 453 | { 454 | "cell_type": "code", 455 | "execution_count": 50, 456 | "metadata": { 457 | "collapsed": false 458 | }, 459 | "outputs": [], 460 | "source": [ 461 | "mm = MoneyMaker('₹')" 462 | ] 463 | }, 464 | { 465 | "cell_type": "code", 466 | "execution_count": 51, 467 | "metadata": { 468 | "collapsed": false 469 | }, 470 | "outputs": [ 471 | { 472 | "name": "stdout", 473 | "output_type": "stream", 474 | "text": [ 475 | "Calling \n" 476 | ] 477 | }, 478 | { 479 | "data": { 480 | "text/plain": [ 481 | "'₹400'" 482 | ] 483 | }, 484 | "execution_count": 51, 485 | "metadata": {}, 486 | "output_type": "execute_result" 487 | } 488 | ], 489 | "source": [ 490 | "mm.make_money(400)" 491 | ] 492 | }, 493 | { 494 | "cell_type": "code", 495 | "execution_count": 52, 496 | "metadata": { 497 | "collapsed": true 498 | }, 499 | "outputs": [], 500 | "source": [ 501 | "mm = MoneyMaker('$')" 502 | ] 503 | }, 504 | { 505 | "cell_type": "code", 506 | "execution_count": 53, 507 | "metadata": { 508 | "collapsed": false 509 | }, 510 | "outputs": [ 511 | { 512 | "name": "stdout", 513 | "output_type": "stream", 514 | "text": [ 515 | "Calling \n" 516 | ] 517 | }, 518 | { 519 | "data": { 520 | "text/plain": [ 521 | "'$1000'" 522 | ] 523 | }, 524 | "execution_count": 53, 525 | "metadata": {}, 526 | "output_type": "execute_result" 527 | } 528 | ], 529 | "source": [ 530 | "mm.make_money(1000)" 531 | ] 532 | }, 533 | { 534 | "cell_type": "markdown", 535 | "metadata": {}, 536 | "source": [ 537 | "## Preserving Metadata of decorated functions" 538 | ] 539 | }, 540 | { 541 | "cell_type": "code", 542 | "execution_count": 54, 543 | "metadata": { 544 | "collapsed": true 545 | }, 546 | "outputs": [], 547 | "source": [ 548 | "def noop(f):\n", 549 | " def noop_wrapper():\n", 550 | " return f()\n", 551 | " return noop_wrapper" 552 | ] 553 | }, 554 | { 555 | "cell_type": "code", 556 | "execution_count": 55, 557 | "metadata": { 558 | "collapsed": true 559 | }, 560 | "outputs": [], 561 | "source": [ 562 | "@noop\n", 563 | "def hello():\n", 564 | " '''A nice docstring'''\n", 565 | " print('Hello, World!')" 566 | ] 567 | }, 568 | { 569 | "cell_type": "code", 570 | "execution_count": 56, 571 | "metadata": { 572 | "collapsed": false 573 | }, 574 | "outputs": [ 575 | { 576 | "name": "stdout", 577 | "output_type": "stream", 578 | "text": [ 579 | "Hello, World!\n" 580 | ] 581 | } 582 | ], 583 | "source": [ 584 | "hello()" 585 | ] 586 | }, 587 | { 588 | "cell_type": "code", 589 | "execution_count": 58, 590 | "metadata": { 591 | "collapsed": false 592 | }, 593 | "outputs": [ 594 | { 595 | "name": "stdout", 596 | "output_type": "stream", 597 | "text": [ 598 | "Help on function noop_wrapper in module __main__:\n", 599 | "\n", 600 | "noop_wrapper()\n", 601 | "\n" 602 | ] 603 | } 604 | ], 605 | "source": [ 606 | "help(hello) # Losing metadata" 607 | ] 608 | }, 609 | { 610 | "cell_type": "code", 611 | "execution_count": 59, 612 | "metadata": { 613 | "collapsed": false 614 | }, 615 | "outputs": [ 616 | { 617 | "data": { 618 | "text/plain": [ 619 | "'noop_wrapper'" 620 | ] 621 | }, 622 | "execution_count": 59, 623 | "metadata": {}, 624 | "output_type": "execute_result" 625 | } 626 | ], 627 | "source": [ 628 | "hello.__name__" 629 | ] 630 | }, 631 | { 632 | "cell_type": "code", 633 | "execution_count": 60, 634 | "metadata": { 635 | "collapsed": true 636 | }, 637 | "outputs": [], 638 | "source": [ 639 | "hello.__doc__" 640 | ] 641 | }, 642 | { 643 | "cell_type": "markdown", 644 | "metadata": {}, 645 | "source": [ 646 | "### A simple solution" 647 | ] 648 | }, 649 | { 650 | "cell_type": "code", 651 | "execution_count": 81, 652 | "metadata": { 653 | "collapsed": true 654 | }, 655 | "outputs": [], 656 | "source": [ 657 | "def noop(f):\n", 658 | " def noop_wrapper():\n", 659 | " return f()\n", 660 | " \n", 661 | " noop_wrapper.__name__ = f.__name__\n", 662 | " noop_wrapper.__doc__ = f.__doc__\n", 663 | " \n", 664 | " return noop_wrapper" 665 | ] 666 | }, 667 | { 668 | "cell_type": "code", 669 | "execution_count": 82, 670 | "metadata": { 671 | "collapsed": true 672 | }, 673 | "outputs": [], 674 | "source": [ 675 | "def hello():\n", 676 | " '''A simple print function'''\n", 677 | " return 'Hello from {} function, I am {}'.format(hello.__name__, hello.__doc__)" 678 | ] 679 | }, 680 | { 681 | "cell_type": "code", 682 | "execution_count": 83, 683 | "metadata": { 684 | "collapsed": false 685 | }, 686 | "outputs": [ 687 | { 688 | "data": { 689 | "text/plain": [ 690 | "'Hello from hello function, I am A simple print function'" 691 | ] 692 | }, 693 | "execution_count": 83, 694 | "metadata": {}, 695 | "output_type": "execute_result" 696 | } 697 | ], 698 | "source": [ 699 | "hello()" 700 | ] 701 | }, 702 | { 703 | "cell_type": "code", 704 | "execution_count": 86, 705 | "metadata": { 706 | "collapsed": true 707 | }, 708 | "outputs": [], 709 | "source": [ 710 | "@noop\n", 711 | "def hello():\n", 712 | " '''A simple print function'''\n", 713 | " return 'Hello from {} function, I am {}'.format(hello.__name__, hello.__doc__)" 714 | ] 715 | }, 716 | { 717 | "cell_type": "code", 718 | "execution_count": 87, 719 | "metadata": { 720 | "collapsed": false 721 | }, 722 | "outputs": [ 723 | { 724 | "data": { 725 | "text/plain": [ 726 | "'Hello from hello function, I am A simple print function'" 727 | ] 728 | }, 729 | "execution_count": 87, 730 | "metadata": {}, 731 | "output_type": "execute_result" 732 | } 733 | ], 734 | "source": [ 735 | "hello()" 736 | ] 737 | }, 738 | { 739 | "cell_type": "code", 740 | "execution_count": 89, 741 | "metadata": { 742 | "collapsed": false 743 | }, 744 | "outputs": [ 745 | { 746 | "data": { 747 | "text/plain": [ 748 | "'hello'" 749 | ] 750 | }, 751 | "execution_count": 89, 752 | "metadata": {}, 753 | "output_type": "execute_result" 754 | } 755 | ], 756 | "source": [ 757 | "hello.__name__" 758 | ] 759 | }, 760 | { 761 | "cell_type": "markdown", 762 | "metadata": {}, 763 | "source": [ 764 | "### Or a more elengant way using functools" 765 | ] 766 | }, 767 | { 768 | "cell_type": "code", 769 | "execution_count": 91, 770 | "metadata": { 771 | "collapsed": true 772 | }, 773 | "outputs": [], 774 | "source": [ 775 | "from functools import wraps" 776 | ] 777 | }, 778 | { 779 | "cell_type": "code", 780 | "execution_count": 103, 781 | "metadata": { 782 | "collapsed": true 783 | }, 784 | "outputs": [], 785 | "source": [ 786 | "def noop(f):\n", 787 | " \n", 788 | " @wraps(f)\n", 789 | " def noop_wrapper():\n", 790 | " return f()\n", 791 | " \n", 792 | " return noop_wrapper" 793 | ] 794 | }, 795 | { 796 | "cell_type": "code", 797 | "execution_count": 108, 798 | "metadata": { 799 | "collapsed": false 800 | }, 801 | "outputs": [], 802 | "source": [ 803 | "@noop\n", 804 | "def jello():\n", 805 | " '''I print jello'''\n", 806 | " return 'jello from {} and {}'.format(jello.__name__, jello.__doc__)" 807 | ] 808 | }, 809 | { 810 | "cell_type": "code", 811 | "execution_count": 109, 812 | "metadata": { 813 | "collapsed": false 814 | }, 815 | "outputs": [ 816 | { 817 | "data": { 818 | "text/plain": [ 819 | "'jello from jello and I print jello'" 820 | ] 821 | }, 822 | "execution_count": 109, 823 | "metadata": {}, 824 | "output_type": "execute_result" 825 | } 826 | ], 827 | "source": [ 828 | "jello()" 829 | ] 830 | }, 831 | { 832 | "cell_type": "markdown", 833 | "metadata": {}, 834 | "source": [ 835 | "## Another example" 836 | ] 837 | }, 838 | { 839 | "cell_type": "code", 840 | "execution_count": 113, 841 | "metadata": { 842 | "collapsed": true 843 | }, 844 | "outputs": [], 845 | "source": [ 846 | "def check_no_neg(index):\n", 847 | " def validator(f):\n", 848 | " def wrap(*args):\n", 849 | " if args[index] < 0:\n", 850 | " raise ValueError('Argument {} must be non-negative'.format(index))\n", 851 | " return f(*args)\n", 852 | " return wrap\n", 853 | " return validator" 854 | ] 855 | }, 856 | { 857 | "cell_type": "code", 858 | "execution_count": 114, 859 | "metadata": { 860 | "collapsed": true 861 | }, 862 | "outputs": [], 863 | "source": [ 864 | "@check_no_neg(1)\n", 865 | "def create_list(value, size):\n", 866 | " return [value] * size" 867 | ] 868 | }, 869 | { 870 | "cell_type": "code", 871 | "execution_count": 116, 872 | "metadata": { 873 | "collapsed": false 874 | }, 875 | "outputs": [ 876 | { 877 | "data": { 878 | "text/plain": [ 879 | "[1, 1, 1]" 880 | ] 881 | }, 882 | "execution_count": 116, 883 | "metadata": {}, 884 | "output_type": "execute_result" 885 | } 886 | ], 887 | "source": [ 888 | "create_list(1, 3)" 889 | ] 890 | }, 891 | { 892 | "cell_type": "code", 893 | "execution_count": 119, 894 | "metadata": { 895 | "collapsed": false 896 | }, 897 | "outputs": [ 898 | { 899 | "name": "stdout", 900 | "output_type": "stream", 901 | "text": [ 902 | "Size argument is negative\n" 903 | ] 904 | } 905 | ], 906 | "source": [ 907 | "try:\n", 908 | " create_list(1, -1)\n", 909 | "except ValueError:\n", 910 | " print('Size argument is negative')" 911 | ] 912 | } 913 | ], 914 | "metadata": { 915 | "kernelspec": { 916 | "display_name": "Python [conda root]", 917 | "language": "python", 918 | "name": "conda-root-py" 919 | }, 920 | "language_info": { 921 | "codemirror_mode": { 922 | "name": "ipython", 923 | "version": 3 924 | }, 925 | "file_extension": ".py", 926 | "mimetype": "text/x-python", 927 | "name": "python", 928 | "nbconvert_exporter": "python", 929 | "pygments_lexer": "ipython3", 930 | "version": "3.5.2" 931 | } 932 | }, 933 | "nbformat": 4, 934 | "nbformat_minor": 2 935 | } 936 | -------------------------------------------------------------------------------- /005_Class_Methods/ShippingContainers.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # -*- coding: utf-8 -*- 3 | """ 4 | Created on Thu Feb 23 08:11:18 2017 5 | 6 | @author: ArchKudo 7 | """ 8 | 9 | import iso6346 10 | 11 | 12 | class ShippingContainer: 13 | '''The ShippingContainer base class''' 14 | serial = 0 # A class variable 15 | 16 | HEIGHT_FT = 100 17 | WIDTH_FT = 100 18 | 19 | @staticmethod 20 | def _make_bic_code(owner, serial): 21 | # [owner] + [category] + [serial no.] + [check] 22 | return iso6346.create(owner_code=owner, serial=str(serial).zfill(6)) 23 | 24 | @classmethod 25 | def _get_serial(cls): 26 | # Add class as argument 27 | result = cls.serial 28 | cls.serial += 1 29 | return result 30 | 31 | @classmethod 32 | def create_empty(cls, owner, *args, **kwargs): 33 | '''To accomodate extra args of child class''' 34 | return cls(owner, contents=None, *args, **kwargs) 35 | 36 | @classmethod 37 | def create_with_items(cls, owner, contents, *args, **kwargs): 38 | '''To accomodate extra args of child class''' 39 | return cls(owner, contents, *args, **kwargs) 40 | 41 | def __init__(self, owner, contents, length_ft): 42 | self.contents = contents 43 | self.length_ft = length_ft 44 | # Static methods can change instance and not the class object and hence, 45 | # the self._make_bic_code instead of ShippingContainer._make_bic_code 46 | self.bic_code = self._make_bic_code( 47 | owner=owner, serial=ShippingContainer._get_serial()) 48 | 49 | def _calc_volume(self): 50 | # The real volume function which needs to be overrided in child class 51 | return ShippingContainer.HEIGHT_FT * ShippingContainer.WIDTH_FT * self.length_ft 52 | 53 | @property 54 | def volume_ft3(self): 55 | '''Calls _calc_volume to calculate volume''' 56 | return self._calc_volume() 57 | 58 | 59 | class RefrigeratedShippingContainer(ShippingContainer): 60 | '''Shipping container class with temperature control''' 61 | 62 | MAX_TEMP = 4.0 63 | FRIDGE_VOLUME = 100 64 | 65 | @staticmethod 66 | def _f_to_c(fahrenheit): 67 | # Convert fahrenheit to celsius 68 | return (fahrenheit - 32) * 5 / 9 69 | 70 | @staticmethod 71 | def _c_to_f(celsius): 72 | # Convert celsius to fahrenheit 73 | return (celsius) * 9 / 5 + 32 74 | 75 | @staticmethod 76 | def _make_bic_code(owner, serial): 77 | # Category R for refrigerated 78 | return iso6346.create(owner_code=owner, serial=str(serial).zfill(6), category='R') 79 | 80 | def __init__(self, owner, contents, length_ft, celsius): 81 | # To get init method of parent 82 | super().__init__(owner, contents, length_ft) 83 | # Equivalent to self._celsius = celsius with celsius.setter checks 84 | self._celsius = None 85 | self.celsius = celsius 86 | 87 | @property 88 | def celsius(self): 89 | '''Check Temperature ''' 90 | return self._celsius 91 | 92 | def _set_celsius(self, value): 93 | if value > RefrigeratedShippingContainer.MAX_TEMP: 94 | raise ValueError('Temperature can\'t be greater than 4°C') 95 | self._celsius = value 96 | 97 | @celsius.setter 98 | def celsius(self, value): 99 | return self._set_celsius(value) 100 | 101 | @property 102 | def fahrenheit(self): 103 | '''Easy fahrenheit setting''' 104 | return RefrigeratedShippingContainer._c_to_f(self.celsius) 105 | 106 | @fahrenheit.setter 107 | def fahrenheit(self, value): 108 | self.celsius = RefrigeratedShippingContainer._f_to_c(value) 109 | 110 | def _calc_volume(self): 111 | return super()._calc_volume() - RefrigeratedShippingContainer.FRIDGE_VOLUME 112 | 113 | 114 | class HeatedRefrigeratedShippingContainer(RefrigeratedShippingContainer): 115 | '''RefrigeratedShippingContainer class with bounded temperature control''' 116 | MIN_CELSIUS = -20.0 117 | 118 | def _set_celsius(self, value): 119 | if value < HeatedRefrigeratedShippingContainer.MIN_CELSIUS: 120 | raise ValueError('Temperature too cold < {}'.format( 121 | HeatedRefrigeratedShippingContainer.MIN_CELSIUS)) 122 | return super()._set_celsius(value) 123 | -------------------------------------------------------------------------------- /005_Class_Methods/iso6346.py: -------------------------------------------------------------------------------- 1 | """ 2 | ISO 6346 shipping container codes. 3 | """ 4 | 5 | 6 | def create(owner_code, serial, category='U'): 7 | """Create an ISO 6346 shipping container code. 8 | 9 | Args: 10 | owner_code (str): Three character alphabetic container code. 11 | serial (str): Six digit numeric serial number. 12 | category (str): Equipment category identifier. 13 | 14 | Returns: 15 | An ISO 6346 container code including a check digit. 16 | 17 | Raises: 18 | ValueError: If incorrect values are provided. 19 | """ 20 | if not (len(owner_code) == 3 and owner_code.isalpha()): 21 | raise ValueError("Invalid ISO 6346 owner code '{}'".format(owner_code)) 22 | 23 | if category not in ('U', 'J', 'Z', 'R'): 24 | raise ValueError("Invalid ISO 6346 category identifier '{}'".format(category)) 25 | 26 | if not (len(serial) == 6 and serial.isdigit()): 27 | raise ValueError("Invalid ISO 6346 serial number") 28 | 29 | raw_code = owner_code + category + serial 30 | full_code = raw_code + str(check_digit(raw_code)) 31 | return full_code 32 | 33 | 34 | def check_digit(raw_code): 35 | """Compute the check digit for an ISO 6346 code without that digit 36 | 37 | Args: 38 | raw_code (str): An ISO 6346 code lacking a check digit. 39 | 40 | Returns: 41 | An integer check digit between 0 and 9 inclusive. 42 | """ 43 | s = sum(code(char) * 2**index for index, char in enumerate(raw_code)) 44 | return s % 11 % 10 45 | 46 | 47 | def code(char): 48 | """Determine the ISO 6346 numeric equivalent of a character. 49 | 50 | Args: 51 | char (str): A single character string. 52 | 53 | Return: 54 | An integer code equivalent to the supplied character. 55 | """ 56 | return int(char) if char.isdigit() else letter_code(char) 57 | 58 | 59 | def letter_code(letter): 60 | """Determine the ISO 6346 numeric code for a letter. 61 | 62 | Args: 63 | letter (str): A single letter. 64 | 65 | Returns: 66 | An integer character code equivalent to the supplied letter. 67 | """ 68 | value = ord(letter.lower()) - ord('a') + 10 69 | return value + value // 11 70 | -------------------------------------------------------------------------------- /005_Class_Methods/static_vs_class.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/005_Class_Methods/static_vs_class.png -------------------------------------------------------------------------------- /006_String and Representations/001_Using __str__, __repr__.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "code", 5 | "execution_count": 5, 6 | "metadata": { 7 | "collapsed": true 8 | }, 9 | "outputs": [], 10 | "source": [ 11 | "class Point2D:\n", 12 | " def __init__(self, x, y):\n", 13 | " self.x, self.y = x, y\n", 14 | " \n", 15 | " # str should give general info\n", 16 | " def __str__(self):\n", 17 | " return '({}, {})'.format(self.x, self.y)\n", 18 | " \n", 19 | " # repr should give debuggging info\n", 20 | " def __repr__(self):\n", 21 | " return 'Point2d({}, {})'.format(self.x, self.y)" 22 | ] 23 | }, 24 | { 25 | "cell_type": "code", 26 | "execution_count": 6, 27 | "metadata": { 28 | "collapsed": true 29 | }, 30 | "outputs": [], 31 | "source": [ 32 | "p1 = Point2D(12, 12)" 33 | ] 34 | }, 35 | { 36 | "cell_type": "code", 37 | "execution_count": 7, 38 | "metadata": { 39 | "collapsed": false 40 | }, 41 | "outputs": [ 42 | { 43 | "data": { 44 | "text/plain": [ 45 | "'(12, 12)'" 46 | ] 47 | }, 48 | "execution_count": 7, 49 | "metadata": {}, 50 | "output_type": "execute_result" 51 | } 52 | ], 53 | "source": [ 54 | "str(p1)" 55 | ] 56 | }, 57 | { 58 | "cell_type": "markdown", 59 | "metadata": {}, 60 | "source": [ 61 | "### repr() should be such as output should be able to create the exact object" 62 | ] 63 | }, 64 | { 65 | "cell_type": "code", 66 | "execution_count": 9, 67 | "metadata": { 68 | "collapsed": false 69 | }, 70 | "outputs": [ 71 | { 72 | "data": { 73 | "text/plain": [ 74 | "'Point2d(12, 12)'" 75 | ] 76 | }, 77 | "execution_count": 9, 78 | "metadata": {}, 79 | "output_type": "execute_result" 80 | } 81 | ], 82 | "source": [ 83 | "repr(p1) " 84 | ] 85 | }, 86 | { 87 | "cell_type": "markdown", 88 | "metadata": {}, 89 | "source": [ 90 | "### Print use str representation" 91 | ] 92 | }, 93 | { 94 | "cell_type": "code", 95 | "execution_count": 10, 96 | "metadata": { 97 | "collapsed": false 98 | }, 99 | "outputs": [ 100 | { 101 | "name": "stdout", 102 | "output_type": "stream", 103 | "text": [ 104 | "(12, 12)\n" 105 | ] 106 | } 107 | ], 108 | "source": [ 109 | "print(p1)" 110 | ] 111 | }, 112 | { 113 | "cell_type": "markdown", 114 | "metadata": {}, 115 | "source": [ 116 | "### DIcts, Lists, Tuples, Set use repr representation" 117 | ] 118 | }, 119 | { 120 | "cell_type": "code", 121 | "execution_count": 21, 122 | "metadata": { 123 | "collapsed": false 124 | }, 125 | "outputs": [ 126 | { 127 | "name": "stdout", 128 | "output_type": "stream", 129 | "text": [ 130 | "(Point2d(1, 1), Point2d(2, 2))\n" 131 | ] 132 | } 133 | ], 134 | "source": [ 135 | "tup = (Point2D(1, 1), Point2D(2, 2))\n", 136 | "print(tup)" 137 | ] 138 | }, 139 | { 140 | "cell_type": "code", 141 | "execution_count": 26, 142 | "metadata": { 143 | "collapsed": false 144 | }, 145 | "outputs": [ 146 | { 147 | "name": "stdout", 148 | "output_type": "stream", 149 | "text": [ 150 | "[Point2d(1, 1), Point2d(2, 2)]\n" 151 | ] 152 | } 153 | ], 154 | "source": [ 155 | "lst = [Point2D(x, x) for x in range(1, 3)]\n", 156 | "print(lst)" 157 | ] 158 | }, 159 | { 160 | "cell_type": "code", 161 | "execution_count": 29, 162 | "metadata": { 163 | "collapsed": false 164 | }, 165 | "outputs": [], 166 | "source": [ 167 | "dk = {lst[x]: tup[x] for x in range(2)}" 168 | ] 169 | }, 170 | { 171 | "cell_type": "code", 172 | "execution_count": 30, 173 | "metadata": { 174 | "collapsed": false 175 | }, 176 | "outputs": [ 177 | { 178 | "name": "stdout", 179 | "output_type": "stream", 180 | "text": [ 181 | "{Point2d(2, 2): Point2d(2, 2), Point2d(1, 1): Point2d(1, 1)}\n" 182 | ] 183 | } 184 | ], 185 | "source": [ 186 | "print(dk)" 187 | ] 188 | }, 189 | { 190 | "cell_type": "code", 191 | "execution_count": 31, 192 | "metadata": { 193 | "collapsed": true 194 | }, 195 | "outputs": [], 196 | "source": [ 197 | "s = {Point2D(1, 1), Point2D(2, 2)}" 198 | ] 199 | }, 200 | { 201 | "cell_type": "code", 202 | "execution_count": 32, 203 | "metadata": { 204 | "collapsed": false 205 | }, 206 | "outputs": [ 207 | { 208 | "name": "stdout", 209 | "output_type": "stream", 210 | "text": [ 211 | "{Point2d(1, 1), Point2d(2, 2)}\n" 212 | ] 213 | } 214 | ], 215 | "source": [ 216 | "print(s)" 217 | ] 218 | }, 219 | { 220 | "cell_type": "markdown", 221 | "metadata": {}, 222 | "source": [ 223 | "## Using \\__format\\__" 224 | ] 225 | }, 226 | { 227 | "cell_type": "code", 228 | "execution_count": 33, 229 | "metadata": { 230 | "collapsed": true 231 | }, 232 | "outputs": [], 233 | "source": [ 234 | "class Point2D:\n", 235 | " def __init__(self, x, y):\n", 236 | " self.x, self.y = x, y\n", 237 | " \n", 238 | " # str should give general info\n", 239 | " def __str__(self):\n", 240 | " return '({}, {})'.format(self.x, self.y)\n", 241 | " \n", 242 | " # repr should give debuggging info\n", 243 | " def __repr__(self):\n", 244 | " return 'Point2d({}, {})'.format(self.x, self.y)\n", 245 | " \n", 246 | " def __format__(self, f):\n", 247 | " if f == 'r':\n", 248 | " return '{} {}'.format(self.y, self.x)\n", 249 | " else:\n", 250 | " return '{} {}'.format(self.x, self.y)" 251 | ] 252 | }, 253 | { 254 | "cell_type": "code", 255 | "execution_count": 34, 256 | "metadata": { 257 | "collapsed": true 258 | }, 259 | "outputs": [], 260 | "source": [ 261 | "p = Point2D(1, 2)" 262 | ] 263 | }, 264 | { 265 | "cell_type": "code", 266 | "execution_count": 35, 267 | "metadata": { 268 | "collapsed": false 269 | }, 270 | "outputs": [ 271 | { 272 | "name": "stdout", 273 | "output_type": "stream", 274 | "text": [ 275 | "1 2\n" 276 | ] 277 | } 278 | ], 279 | "source": [ 280 | "print('{}'.format(p))" 281 | ] 282 | }, 283 | { 284 | "cell_type": "code", 285 | "execution_count": 36, 286 | "metadata": { 287 | "collapsed": false 288 | }, 289 | "outputs": [ 290 | { 291 | "name": "stdout", 292 | "output_type": "stream", 293 | "text": [ 294 | "2 1\n" 295 | ] 296 | } 297 | ], 298 | "source": [ 299 | "print('{:r}'.format(p))" 300 | ] 301 | }, 302 | { 303 | "cell_type": "code", 304 | "execution_count": 37, 305 | "metadata": { 306 | "collapsed": false 307 | }, 308 | "outputs": [ 309 | { 310 | "name": "stdout", 311 | "output_type": "stream", 312 | "text": [ 313 | "(1, 2)\n" 314 | ] 315 | } 316 | ], 317 | "source": [ 318 | "# Force print string\n", 319 | "print('{!s}'.format(p))" 320 | ] 321 | }, 322 | { 323 | "cell_type": "code", 324 | "execution_count": 38, 325 | "metadata": { 326 | "collapsed": false 327 | }, 328 | "outputs": [ 329 | { 330 | "name": "stdout", 331 | "output_type": "stream", 332 | "text": [ 333 | "Point2d(1, 2)\n" 334 | ] 335 | } 336 | ], 337 | "source": [ 338 | "# Force print repr\n", 339 | "print('{!r}'.format(p))" 340 | ] 341 | }, 342 | { 343 | "cell_type": "markdown", 344 | "metadata": { 345 | "collapsed": true 346 | }, 347 | "source": [ 348 | "## Using reprlib\n", 349 | "reprlib is used to represent long output" 350 | ] 351 | }, 352 | { 353 | "cell_type": "code", 354 | "execution_count": 5, 355 | "metadata": { 356 | "collapsed": true 357 | }, 358 | "outputs": [], 359 | "source": [ 360 | "from reprlib import repr" 361 | ] 362 | }, 363 | { 364 | "cell_type": "code", 365 | "execution_count": 6, 366 | "metadata": { 367 | "collapsed": true 368 | }, 369 | "outputs": [], 370 | "source": [ 371 | "lst = [x for x in range(10000)]" 372 | ] 373 | }, 374 | { 375 | "cell_type": "code", 376 | "execution_count": 7, 377 | "metadata": { 378 | "collapsed": false 379 | }, 380 | "outputs": [ 381 | { 382 | "data": { 383 | "text/plain": [ 384 | "'[0, 1, 2, 3, 4, 5, ...]'" 385 | ] 386 | }, 387 | "execution_count": 7, 388 | "metadata": {}, 389 | "output_type": "execute_result" 390 | } 391 | ], 392 | "source": [ 393 | "repr(lst)" 394 | ] 395 | }, 396 | { 397 | "cell_type": "markdown", 398 | "metadata": {}, 399 | "source": [ 400 | "## Another string functions" 401 | ] 402 | }, 403 | { 404 | "cell_type": "markdown", 405 | "metadata": {}, 406 | "source": [ 407 | "### ascii()\n", 408 | "Replace non-ascii characters with escape sequences" 409 | ] 410 | }, 411 | { 412 | "cell_type": "code", 413 | "execution_count": 8, 414 | "metadata": { 415 | "collapsed": false 416 | }, 417 | "outputs": [ 418 | { 419 | "data": { 420 | "text/plain": [ 421 | "\"'I need \\\\u20b9'\"" 422 | ] 423 | }, 424 | "execution_count": 8, 425 | "metadata": {}, 426 | "output_type": "execute_result" 427 | } 428 | ], 429 | "source": [ 430 | "ascii('I need ₹')" 431 | ] 432 | }, 433 | { 434 | "cell_type": "markdown", 435 | "metadata": {}, 436 | "source": [ 437 | "### chr()\n", 438 | "Convert integer Unicode codepoint to single character string" 439 | ] 440 | }, 441 | { 442 | "cell_type": "code", 443 | "execution_count": 9, 444 | "metadata": { 445 | "collapsed": false 446 | }, 447 | "outputs": [ 448 | { 449 | "data": { 450 | "text/plain": [ 451 | "'¾'" 452 | ] 453 | }, 454 | "execution_count": 9, 455 | "metadata": {}, 456 | "output_type": "execute_result" 457 | } 458 | ], 459 | "source": [ 460 | "chr(190)" 461 | ] 462 | }, 463 | { 464 | "cell_type": "markdown", 465 | "metadata": {}, 466 | "source": [ 467 | "### ord()\n", 468 | "Convert single character string to its Unicode integercodepoint" 469 | ] 470 | }, 471 | { 472 | "cell_type": "code", 473 | "execution_count": 10, 474 | "metadata": { 475 | "collapsed": false 476 | }, 477 | "outputs": [ 478 | { 479 | "data": { 480 | "text/plain": [ 481 | "190" 482 | ] 483 | }, 484 | "execution_count": 10, 485 | "metadata": {}, 486 | "output_type": "execute_result" 487 | } 488 | ], 489 | "source": [ 490 | "ord(chr(190))" 491 | ] 492 | }, 493 | { 494 | "cell_type": "code", 495 | "execution_count": null, 496 | "metadata": { 497 | "collapsed": true 498 | }, 499 | "outputs": [], 500 | "source": [] 501 | } 502 | ], 503 | "metadata": { 504 | "kernelspec": { 505 | "display_name": "Python [conda root]", 506 | "language": "python", 507 | "name": "conda-root-py" 508 | }, 509 | "language_info": { 510 | "codemirror_mode": { 511 | "name": "ipython", 512 | "version": 3 513 | }, 514 | "file_extension": ".py", 515 | "mimetype": "text/x-python", 516 | "name": "python", 517 | "nbconvert_exporter": "python", 518 | "pygments_lexer": "ipython3", 519 | "version": "3.5.2" 520 | } 521 | }, 522 | "nbformat": 4, 523 | "nbformat_minor": 2 524 | } 525 | -------------------------------------------------------------------------------- /007_Numeric and scalar datatypes/001_Numbers.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## ints\n", 8 | "Unlimited precision integers" 9 | ] 10 | }, 11 | { 12 | "cell_type": "code", 13 | "execution_count": 1, 14 | "metadata": { 15 | "collapsed": false 16 | }, 17 | "outputs": [ 18 | { 19 | "data": { 20 | "text/plain": [ 21 | "'402387260077093773...0000000000000000000'" 22 | ] 23 | }, 24 | "execution_count": 1, 25 | "metadata": {}, 26 | "output_type": "execute_result" 27 | } 28 | ], 29 | "source": [ 30 | "from math import factorial as fact\n", 31 | "from reprlib import repr\n", 32 | "repr(fact(1000))" 33 | ] 34 | }, 35 | { 36 | "cell_type": "markdown", 37 | "metadata": {}, 38 | "source": [ 39 | "## float\n", 40 | "IEEE-754 Standard\n", 41 | "64 bits(double precision) float \n", 42 | "53 bit of binary precision \n", 43 | "15 to 17 bits of decimal precision " 44 | ] 45 | }, 46 | { 47 | "cell_type": "code", 48 | "execution_count": 2, 49 | "metadata": { 50 | "collapsed": true 51 | }, 52 | "outputs": [], 53 | "source": [ 54 | "from sys import float_info" 55 | ] 56 | }, 57 | { 58 | "cell_type": "code", 59 | "execution_count": 3, 60 | "metadata": { 61 | "collapsed": false 62 | }, 63 | "outputs": [ 64 | { 65 | "data": { 66 | "text/plain": [ 67 | "sys.float_info(max=1.7976931348623157e+308, max_exp=1024, max_10_exp=308, min=2.2250738585072014e-308, min_exp=-1021, min_10_exp=-307, dig=15, mant_dig=53, epsilon=2.220446049250313e-16, radix=2, rounds=1)" 68 | ] 69 | }, 70 | "execution_count": 3, 71 | "metadata": {}, 72 | "output_type": "execute_result" 73 | } 74 | ], 75 | "source": [ 76 | "float_info" 77 | ] 78 | }, 79 | { 80 | "cell_type": "markdown", 81 | "metadata": {}, 82 | "source": [ 83 | "### Precision in float" 84 | ] 85 | }, 86 | { 87 | "cell_type": "code", 88 | "execution_count": 4, 89 | "metadata": { 90 | "collapsed": false 91 | }, 92 | "outputs": [ 93 | { 94 | "data": { 95 | "text/plain": [ 96 | "9007199254740992.0" 97 | ] 98 | }, 99 | "execution_count": 4, 100 | "metadata": {}, 101 | "output_type": "execute_result" 102 | } 103 | ], 104 | "source": [ 105 | "float(2**53)" 106 | ] 107 | }, 108 | { 109 | "cell_type": "code", 110 | "execution_count": 6, 111 | "metadata": { 112 | "collapsed": false 113 | }, 114 | "outputs": [ 115 | { 116 | "data": { 117 | "text/plain": [ 118 | "9007199254740992.0" 119 | ] 120 | }, 121 | "execution_count": 6, 122 | "metadata": {}, 123 | "output_type": "execute_result" 124 | } 125 | ], 126 | "source": [ 127 | "float(2**53 + 1) # No Change" 128 | ] 129 | }, 130 | { 131 | "cell_type": "code", 132 | "execution_count": 7, 133 | "metadata": { 134 | "collapsed": false 135 | }, 136 | "outputs": [ 137 | { 138 | "data": { 139 | "text/plain": [ 140 | "9007199254740994.0" 141 | ] 142 | }, 143 | "execution_count": 7, 144 | "metadata": {}, 145 | "output_type": "execute_result" 146 | } 147 | ], 148 | "source": [ 149 | "float(2**53 + 2)" 150 | ] 151 | }, 152 | { 153 | "cell_type": "code", 154 | "execution_count": 13, 155 | "metadata": { 156 | "collapsed": false 157 | }, 158 | "outputs": [ 159 | { 160 | "data": { 161 | "text/plain": [ 162 | "9007199254740996.0" 163 | ] 164 | }, 165 | "execution_count": 13, 166 | "metadata": {}, 167 | "output_type": "execute_result" 168 | } 169 | ], 170 | "source": [ 171 | "float(2**53 + 3) # Changes by 2" 172 | ] 173 | }, 174 | { 175 | "cell_type": "code", 176 | "execution_count": 17, 177 | "metadata": { 178 | "collapsed": false 179 | }, 180 | "outputs": [ 181 | { 182 | "data": { 183 | "text/plain": [ 184 | "0.7000000000000001" 185 | ] 186 | }, 187 | "execution_count": 17, 188 | "metadata": {}, 189 | "output_type": "execute_result" 190 | } 191 | ], 192 | "source": [ 193 | "float(0.8 - 0.1)" 194 | ] 195 | }, 196 | { 197 | "cell_type": "markdown", 198 | "metadata": {}, 199 | "source": [ 200 | "## Precision using decimal" 201 | ] 202 | }, 203 | { 204 | "cell_type": "code", 205 | "execution_count": 14, 206 | "metadata": { 207 | "collapsed": true 208 | }, 209 | "outputs": [], 210 | "source": [ 211 | "import decimal" 212 | ] 213 | }, 214 | { 215 | "cell_type": "code", 216 | "execution_count": 16, 217 | "metadata": { 218 | "collapsed": false 219 | }, 220 | "outputs": [ 221 | { 222 | "data": { 223 | "text/plain": [ 224 | "Context(prec=28, rounding=ROUND_HALF_EVEN, Emin=-999999, Emax=999999, capitals=1, clamp=0, flags=[], traps=[InvalidOperation, DivisionByZero, Overflow])" 225 | ] 226 | }, 227 | "execution_count": 16, 228 | "metadata": {}, 229 | "output_type": "execute_result" 230 | } 231 | ], 232 | "source": [ 233 | "decimal.getcontext() # 28 bits of precision" 234 | ] 235 | }, 236 | { 237 | "cell_type": "code", 238 | "execution_count": 22, 239 | "metadata": { 240 | "collapsed": true 241 | }, 242 | "outputs": [], 243 | "source": [ 244 | "from decimal import Decimal as d" 245 | ] 246 | }, 247 | { 248 | "cell_type": "code", 249 | "execution_count": 23, 250 | "metadata": { 251 | "collapsed": false 252 | }, 253 | "outputs": [ 254 | { 255 | "data": { 256 | "text/plain": [ 257 | "Decimal('19')" 258 | ] 259 | }, 260 | "execution_count": 23, 261 | "metadata": {}, 262 | "output_type": "execute_result" 263 | } 264 | ], 265 | "source": [ 266 | "d(19)" 267 | ] 268 | }, 269 | { 270 | "cell_type": "code", 271 | "execution_count": 24, 272 | "metadata": { 273 | "collapsed": false 274 | }, 275 | "outputs": [ 276 | { 277 | "data": { 278 | "text/plain": [ 279 | "Decimal('19')" 280 | ] 281 | }, 282 | "execution_count": 24, 283 | "metadata": {}, 284 | "output_type": "execute_result" 285 | } 286 | ], 287 | "source": [ 288 | "d('19')" 289 | ] 290 | }, 291 | { 292 | "cell_type": "code", 293 | "execution_count": 25, 294 | "metadata": { 295 | "collapsed": false 296 | }, 297 | "outputs": [ 298 | { 299 | "data": { 300 | "text/plain": [ 301 | "Decimal('0.1')" 302 | ] 303 | }, 304 | "execution_count": 25, 305 | "metadata": {}, 306 | "output_type": "execute_result" 307 | } 308 | ], 309 | "source": [ 310 | "d('0.8') - d('0.7') # Correct answer" 311 | ] 312 | }, 313 | { 314 | "cell_type": "code", 315 | "execution_count": 27, 316 | "metadata": { 317 | "collapsed": false 318 | }, 319 | "outputs": [ 320 | { 321 | "data": { 322 | "text/plain": [ 323 | "Decimal('0.1000000000000000888178419700')" 324 | ] 325 | }, 326 | "execution_count": 27, 327 | "metadata": {}, 328 | "output_type": "execute_result" 329 | } 330 | ], 331 | "source": [ 332 | "# Argument is float, and is itelf not precise\n", 333 | "d(0.8) - d(0.7)" 334 | ] 335 | }, 336 | { 337 | "cell_type": "markdown", 338 | "metadata": {}, 339 | "source": [ 340 | "### Other operations" 341 | ] 342 | }, 343 | { 344 | "cell_type": "code", 345 | "execution_count": 30, 346 | "metadata": { 347 | "collapsed": false 348 | }, 349 | "outputs": [ 350 | { 351 | "name": "stdout", 352 | "output_type": "stream", 353 | "text": [ 354 | "1\n", 355 | "1.0\n", 356 | "1.00\n", 357 | "5\n", 358 | "5.0\n", 359 | "5.00\n" 360 | ] 361 | } 362 | ], 363 | "source": [ 364 | "# Precision is preserved\n", 365 | "\n", 366 | "print(d(1))\n", 367 | "print(d('1.0'))\n", 368 | "print(d('1.00'))\n", 369 | "\n", 370 | "print(d(1) * 5)\n", 371 | "print(d('1.0') * 5)\n", 372 | "print(d('1.00') * 5)" 373 | ] 374 | }, 375 | { 376 | "cell_type": "code", 377 | "execution_count": 36, 378 | "metadata": { 379 | "collapsed": false 380 | }, 381 | "outputs": [ 382 | { 383 | "name": "stdout", 384 | "output_type": "stream", 385 | "text": [ 386 | "Infinity\n", 387 | "Infinity\n", 388 | "NaN\n", 389 | "-Infinity\n", 390 | "NaN\n" 391 | ] 392 | } 393 | ], 394 | "source": [ 395 | "# Representing NaN and Infinity\n", 396 | "print(d('Infinity'))\n", 397 | "print(d('Infinity') + 10)\n", 398 | "print(d('NaN'))\n", 399 | "print(d('-Infinity'))\n", 400 | "print(d('NaN') + 10)" 401 | ] 402 | }, 403 | { 404 | "cell_type": "code", 405 | "execution_count": 42, 406 | "metadata": { 407 | "collapsed": false 408 | }, 409 | "outputs": [ 410 | { 411 | "name": "stdout", 412 | "output_type": "stream", 413 | "text": [ 414 | "2\n", 415 | "-1\n", 416 | "-3\n", 417 | "-2\n" 418 | ] 419 | } 420 | ], 421 | "source": [ 422 | "# Using Modulo\n", 423 | "\n", 424 | "# Float return difference between number and the first smaller multiple not greater than the number\n", 425 | "print((-7) % 3) # Returns -7 - (-9)\n", 426 | "\n", 427 | "# Decimal return difference between number and nearest multiple reaching zero\n", 428 | "print(d(-7) % 3) # Returns -7 - (-6)\n", 429 | "\n", 430 | "# Using Floor Division using above logic\n", 431 | "print((-7) // 3)\n", 432 | "print(d(-7) // 3)" 433 | ] 434 | }, 435 | { 436 | "cell_type": "markdown", 437 | "metadata": {}, 438 | "source": [ 439 | "## Fractions module" 440 | ] 441 | }, 442 | { 443 | "cell_type": "code", 444 | "execution_count": 43, 445 | "metadata": { 446 | "collapsed": true 447 | }, 448 | "outputs": [], 449 | "source": [ 450 | "from fractions import Fraction as f" 451 | ] 452 | }, 453 | { 454 | "cell_type": "code", 455 | "execution_count": 44, 456 | "metadata": { 457 | "collapsed": false 458 | }, 459 | "outputs": [ 460 | { 461 | "data": { 462 | "text/plain": [ 463 | "Fraction(22, 7)" 464 | ] 465 | }, 466 | "execution_count": 44, 467 | "metadata": {}, 468 | "output_type": "execute_result" 469 | } 470 | ], 471 | "source": [ 472 | "f(22, 7)" 473 | ] 474 | }, 475 | { 476 | "cell_type": "code", 477 | "execution_count": 51, 478 | "metadata": { 479 | "collapsed": false 480 | }, 481 | "outputs": [ 482 | { 483 | "data": { 484 | "text/plain": [ 485 | "Fraction(1, 10)" 486 | ] 487 | }, 488 | "execution_count": 51, 489 | "metadata": {}, 490 | "output_type": "execute_result" 491 | } 492 | ], 493 | "source": [ 494 | "f('1/10')" 495 | ] 496 | }, 497 | { 498 | "cell_type": "code", 499 | "execution_count": 47, 500 | "metadata": { 501 | "collapsed": false 502 | }, 503 | "outputs": [ 504 | { 505 | "data": { 506 | "text/plain": [ 507 | "Fraction(3602879701896397, 36028797018963968)" 508 | ] 509 | }, 510 | "execution_count": 47, 511 | "metadata": {}, 512 | "output_type": "execute_result" 513 | } 514 | ], 515 | "source": [ 516 | "f(0.1)" 517 | ] 518 | }, 519 | { 520 | "cell_type": "code", 521 | "execution_count": 52, 522 | "metadata": { 523 | "collapsed": false 524 | }, 525 | "outputs": [ 526 | { 527 | "data": { 528 | "text/plain": [ 529 | "Fraction(1, 10)" 530 | ] 531 | }, 532 | "execution_count": 52, 533 | "metadata": {}, 534 | "output_type": "execute_result" 535 | } 536 | ], 537 | "source": [ 538 | "f(d('0.1'))" 539 | ] 540 | }, 541 | { 542 | "cell_type": "code", 543 | "execution_count": 54, 544 | "metadata": { 545 | "collapsed": false 546 | }, 547 | "outputs": [ 548 | { 549 | "data": { 550 | "text/plain": [ 551 | "Fraction(13, 15)" 552 | ] 553 | }, 554 | "execution_count": 54, 555 | "metadata": {}, 556 | "output_type": "execute_result" 557 | } 558 | ], 559 | "source": [ 560 | "f('2/3') + f ('1/5')" 561 | ] 562 | }, 563 | { 564 | "cell_type": "code", 565 | "execution_count": 55, 566 | "metadata": { 567 | "collapsed": false 568 | }, 569 | "outputs": [ 570 | { 571 | "data": { 572 | "text/plain": [ 573 | "Fraction(22, 15)" 574 | ] 575 | }, 576 | "execution_count": 55, 577 | "metadata": {}, 578 | "output_type": "execute_result" 579 | } 580 | ], 581 | "source": [ 582 | "f('22/7') * f('7/15')" 583 | ] 584 | }, 585 | { 586 | "cell_type": "code", 587 | "execution_count": 56, 588 | "metadata": { 589 | "collapsed": false 590 | }, 591 | "outputs": [ 592 | { 593 | "data": { 594 | "text/plain": [ 595 | "Fraction(1, 6)" 596 | ] 597 | }, 598 | "execution_count": 56, 599 | "metadata": {}, 600 | "output_type": "execute_result" 601 | } 602 | ], 603 | "source": [ 604 | "f('2/3') % f('1/2')" 605 | ] 606 | }, 607 | { 608 | "cell_type": "markdown", 609 | "metadata": {}, 610 | "source": [ 611 | "## Using complex" 612 | ] 613 | }, 614 | { 615 | "cell_type": "code", 616 | "execution_count": 63, 617 | "metadata": { 618 | "collapsed": false 619 | }, 620 | "outputs": [], 621 | "source": [ 622 | "c = 1 + 2j" 623 | ] 624 | }, 625 | { 626 | "cell_type": "code", 627 | "execution_count": 64, 628 | "metadata": { 629 | "collapsed": false 630 | }, 631 | "outputs": [ 632 | { 633 | "data": { 634 | "text/plain": [ 635 | "1.0" 636 | ] 637 | }, 638 | "execution_count": 64, 639 | "metadata": {}, 640 | "output_type": "execute_result" 641 | } 642 | ], 643 | "source": [ 644 | "c.real" 645 | ] 646 | }, 647 | { 648 | "cell_type": "code", 649 | "execution_count": 65, 650 | "metadata": { 651 | "collapsed": false 652 | }, 653 | "outputs": [ 654 | { 655 | "data": { 656 | "text/plain": [ 657 | "2.0" 658 | ] 659 | }, 660 | "execution_count": 65, 661 | "metadata": {}, 662 | "output_type": "execute_result" 663 | } 664 | ], 665 | "source": [ 666 | "c.imag" 667 | ] 668 | }, 669 | { 670 | "cell_type": "code", 671 | "execution_count": 67, 672 | "metadata": { 673 | "collapsed": false 674 | }, 675 | "outputs": [ 676 | { 677 | "data": { 678 | "text/plain": [ 679 | "(1-2j)" 680 | ] 681 | }, 682 | "execution_count": 67, 683 | "metadata": {}, 684 | "output_type": "execute_result" 685 | } 686 | ], 687 | "source": [ 688 | "c.conjugate()" 689 | ] 690 | }, 691 | { 692 | "cell_type": "markdown", 693 | "metadata": {}, 694 | "source": [ 695 | "### Using cmath" 696 | ] 697 | }, 698 | { 699 | "cell_type": "code", 700 | "execution_count": 68, 701 | "metadata": { 702 | "collapsed": true 703 | }, 704 | "outputs": [], 705 | "source": [ 706 | "import cmath as cx" 707 | ] 708 | }, 709 | { 710 | "cell_type": "code", 711 | "execution_count": 69, 712 | "metadata": { 713 | "collapsed": false 714 | }, 715 | "outputs": [ 716 | { 717 | "data": { 718 | "text/plain": [ 719 | "1j" 720 | ] 721 | }, 722 | "execution_count": 69, 723 | "metadata": {}, 724 | "output_type": "execute_result" 725 | } 726 | ], 727 | "source": [ 728 | "cx.sqrt(-1)" 729 | ] 730 | }, 731 | { 732 | "cell_type": "code", 733 | "execution_count": 70, 734 | "metadata": { 735 | "collapsed": false 736 | }, 737 | "outputs": [ 738 | { 739 | "data": { 740 | "text/plain": [ 741 | "0.7853981633974483" 742 | ] 743 | }, 744 | "execution_count": 70, 745 | "metadata": {}, 746 | "output_type": "execute_result" 747 | } 748 | ], 749 | "source": [ 750 | "cx.phase(1+1j)" 751 | ] 752 | }, 753 | { 754 | "cell_type": "code", 755 | "execution_count": 72, 756 | "metadata": { 757 | "collapsed": false 758 | }, 759 | "outputs": [ 760 | { 761 | "data": { 762 | "text/plain": [ 763 | "0.7615941559557649j" 764 | ] 765 | }, 766 | "execution_count": 72, 767 | "metadata": {}, 768 | "output_type": "execute_result" 769 | } 770 | ], 771 | "source": [ 772 | "cx.tan(1j)" 773 | ] 774 | }, 775 | { 776 | "cell_type": "code", 777 | "execution_count": 73, 778 | "metadata": { 779 | "collapsed": false 780 | }, 781 | "outputs": [ 782 | { 783 | "data": { 784 | "text/plain": [ 785 | "1.4142135623730951" 786 | ] 787 | }, 788 | "execution_count": 73, 789 | "metadata": {}, 790 | "output_type": "execute_result" 791 | } 792 | ], 793 | "source": [ 794 | "abs(1+1j)" 795 | ] 796 | }, 797 | { 798 | "cell_type": "code", 799 | "execution_count": 74, 800 | "metadata": { 801 | "collapsed": true 802 | }, 803 | "outputs": [], 804 | "source": [ 805 | "mod, phase = cx.polar(1 + 1j)" 806 | ] 807 | }, 808 | { 809 | "cell_type": "code", 810 | "execution_count": 75, 811 | "metadata": { 812 | "collapsed": false 813 | }, 814 | "outputs": [ 815 | { 816 | "data": { 817 | "text/plain": [ 818 | "1.4142135623730951" 819 | ] 820 | }, 821 | "execution_count": 75, 822 | "metadata": {}, 823 | "output_type": "execute_result" 824 | } 825 | ], 826 | "source": [ 827 | "mod" 828 | ] 829 | }, 830 | { 831 | "cell_type": "code", 832 | "execution_count": 76, 833 | "metadata": { 834 | "collapsed": false 835 | }, 836 | "outputs": [ 837 | { 838 | "data": { 839 | "text/plain": [ 840 | "0.7853981633974483" 841 | ] 842 | }, 843 | "execution_count": 76, 844 | "metadata": {}, 845 | "output_type": "execute_result" 846 | } 847 | ], 848 | "source": [ 849 | "phase" 850 | ] 851 | }, 852 | { 853 | "cell_type": "code", 854 | "execution_count": 77, 855 | "metadata": { 856 | "collapsed": false 857 | }, 858 | "outputs": [ 859 | { 860 | "data": { 861 | "text/plain": [ 862 | "(1.0000000000000002+1j)" 863 | ] 864 | }, 865 | "execution_count": 77, 866 | "metadata": {}, 867 | "output_type": "execute_result" 868 | } 869 | ], 870 | "source": [ 871 | "cx.rect(mod, phase)" 872 | ] 873 | }, 874 | { 875 | "cell_type": "markdown", 876 | "metadata": {}, 877 | "source": [ 878 | "## abs()\n", 879 | "Returns distance from zero" 880 | ] 881 | }, 882 | { 883 | "cell_type": "code", 884 | "execution_count": 78, 885 | "metadata": { 886 | "collapsed": false 887 | }, 888 | "outputs": [ 889 | { 890 | "data": { 891 | "text/plain": [ 892 | "10" 893 | ] 894 | }, 895 | "execution_count": 78, 896 | "metadata": {}, 897 | "output_type": "execute_result" 898 | } 899 | ], 900 | "source": [ 901 | "abs(10)" 902 | ] 903 | }, 904 | { 905 | "cell_type": "code", 906 | "execution_count": 79, 907 | "metadata": { 908 | "collapsed": false 909 | }, 910 | "outputs": [ 911 | { 912 | "data": { 913 | "text/plain": [ 914 | "1" 915 | ] 916 | }, 917 | "execution_count": 79, 918 | "metadata": {}, 919 | "output_type": "execute_result" 920 | } 921 | ], 922 | "source": [ 923 | "abs(-1)" 924 | ] 925 | }, 926 | { 927 | "cell_type": "code", 928 | "execution_count": 80, 929 | "metadata": { 930 | "collapsed": false 931 | }, 932 | "outputs": [ 933 | { 934 | "data": { 935 | "text/plain": [ 936 | "1.5" 937 | ] 938 | }, 939 | "execution_count": 80, 940 | "metadata": {}, 941 | "output_type": "execute_result" 942 | } 943 | ], 944 | "source": [ 945 | "abs(-1.5)" 946 | ] 947 | }, 948 | { 949 | "cell_type": "code", 950 | "execution_count": 81, 951 | "metadata": { 952 | "collapsed": false 953 | }, 954 | "outputs": [ 955 | { 956 | "data": { 957 | "text/plain": [ 958 | "Fraction(2, 1)" 959 | ] 960 | }, 961 | "execution_count": 81, 962 | "metadata": {}, 963 | "output_type": "execute_result" 964 | } 965 | ], 966 | "source": [ 967 | "abs(f(2, 1))" 968 | ] 969 | }, 970 | { 971 | "cell_type": "markdown", 972 | "metadata": {}, 973 | "source": [ 974 | "## round()\n", 975 | "Rounds to specific decimal places" 976 | ] 977 | }, 978 | { 979 | "cell_type": "code", 980 | "execution_count": 82, 981 | "metadata": { 982 | "collapsed": false 983 | }, 984 | "outputs": [ 985 | { 986 | "data": { 987 | "text/plain": [ 988 | "0.121" 989 | ] 990 | }, 991 | "execution_count": 82, 992 | "metadata": {}, 993 | "output_type": "execute_result" 994 | } 995 | ], 996 | "source": [ 997 | "round(0.121212, 3)" 998 | ] 999 | }, 1000 | { 1001 | "cell_type": "code", 1002 | "execution_count": 84, 1003 | "metadata": { 1004 | "collapsed": false 1005 | }, 1006 | "outputs": [ 1007 | { 1008 | "data": { 1009 | "text/plain": [ 1010 | "True" 1011 | ] 1012 | }, 1013 | "execution_count": 84, 1014 | "metadata": {}, 1015 | "output_type": "execute_result" 1016 | } 1017 | ], 1018 | "source": [ 1019 | "round(1.5) == round(2.5) # Odd is rounded of to higher even to lower integer" 1020 | ] 1021 | }, 1022 | { 1023 | "cell_type": "markdown", 1024 | "metadata": {}, 1025 | "source": [ 1026 | "## Number conversion" 1027 | ] 1028 | }, 1029 | { 1030 | "cell_type": "code", 1031 | "execution_count": 93, 1032 | "metadata": { 1033 | "collapsed": false 1034 | }, 1035 | "outputs": [ 1036 | { 1037 | "data": { 1038 | "text/plain": [ 1039 | "15" 1040 | ] 1041 | }, 1042 | "execution_count": 93, 1043 | "metadata": {}, 1044 | "output_type": "execute_result" 1045 | } 1046 | ], 1047 | "source": [ 1048 | "int('f', base=16)" 1049 | ] 1050 | }, 1051 | { 1052 | "cell_type": "code", 1053 | "execution_count": 88, 1054 | "metadata": { 1055 | "collapsed": false 1056 | }, 1057 | "outputs": [ 1058 | { 1059 | "data": { 1060 | "text/plain": [ 1061 | "'0b1100'" 1062 | ] 1063 | }, 1064 | "execution_count": 88, 1065 | "metadata": {}, 1066 | "output_type": "execute_result" 1067 | } 1068 | ], 1069 | "source": [ 1070 | "bin(12)" 1071 | ] 1072 | }, 1073 | { 1074 | "cell_type": "code", 1075 | "execution_count": 89, 1076 | "metadata": { 1077 | "collapsed": false 1078 | }, 1079 | "outputs": [ 1080 | { 1081 | "data": { 1082 | "text/plain": [ 1083 | "'0o12'" 1084 | ] 1085 | }, 1086 | "execution_count": 89, 1087 | "metadata": {}, 1088 | "output_type": "execute_result" 1089 | } 1090 | ], 1091 | "source": [ 1092 | "oct(10)" 1093 | ] 1094 | }, 1095 | { 1096 | "cell_type": "code", 1097 | "execution_count": 90, 1098 | "metadata": { 1099 | "collapsed": false 1100 | }, 1101 | "outputs": [ 1102 | { 1103 | "data": { 1104 | "text/plain": [ 1105 | "'0x10'" 1106 | ] 1107 | }, 1108 | "execution_count": 90, 1109 | "metadata": {}, 1110 | "output_type": "execute_result" 1111 | } 1112 | ], 1113 | "source": [ 1114 | "hex(16)" 1115 | ] 1116 | }, 1117 | { 1118 | "cell_type": "code", 1119 | "execution_count": 95, 1120 | "metadata": { 1121 | "collapsed": false 1122 | }, 1123 | "outputs": [ 1124 | { 1125 | "data": { 1126 | "text/plain": [ 1127 | "'f'" 1128 | ] 1129 | }, 1130 | "execution_count": 95, 1131 | "metadata": {}, 1132 | "output_type": "execute_result" 1133 | } 1134 | ], 1135 | "source": [ 1136 | "hex(15)[2:]" 1137 | ] 1138 | }, 1139 | { 1140 | "cell_type": "code", 1141 | "execution_count": null, 1142 | "metadata": { 1143 | "collapsed": true 1144 | }, 1145 | "outputs": [], 1146 | "source": [] 1147 | } 1148 | ], 1149 | "metadata": { 1150 | "kernelspec": { 1151 | "display_name": "Python [conda root]", 1152 | "language": "python", 1153 | "name": "conda-root-py" 1154 | }, 1155 | "language_info": { 1156 | "codemirror_mode": { 1157 | "name": "ipython", 1158 | "version": 3 1159 | }, 1160 | "file_extension": ".py", 1161 | "mimetype": "text/x-python", 1162 | "name": "python", 1163 | "nbconvert_exporter": "python", 1164 | "pygments_lexer": "ipython3", 1165 | "version": "3.5.2" 1166 | } 1167 | }, 1168 | "nbformat": 4, 1169 | "nbformat_minor": 2 1170 | } 1171 | -------------------------------------------------------------------------------- /008_Iterables and Iteration/001_Comprehensions, map(), filter(), reduce().ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Multiple input comprehensions" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 5, 13 | "metadata": { 14 | "collapsed": false 15 | }, 16 | "outputs": [ 17 | { 18 | "name": "stdout", 19 | "output_type": "stream", 20 | "text": [ 21 | "[(0, 0), (0, 1), (0, 2), (1, 0), (1, 1), (1, 2), (2, 0), (2, 1), (2, 2), (3, 0), (3, 1), (3, 2), (4, 0), (4, 1), (4, 2)]\n" 22 | ] 23 | } 24 | ], 25 | "source": [ 26 | "# Comprehenion 1\n", 27 | "# [(input vars) (earlier for-clause) (latter for clause)]\n", 28 | "l = [(x, y) for x in range(5) for y in range(3)]\n", 29 | "print(l)" 30 | ] 31 | }, 32 | { 33 | "cell_type": "code", 34 | "execution_count": 6, 35 | "metadata": { 36 | "collapsed": false 37 | }, 38 | "outputs": [ 39 | { 40 | "name": "stdout", 41 | "output_type": "stream", 42 | "text": [ 43 | "[(0, 0), (0, 1), (0, 2), (1, 0), (1, 1), (1, 2), (2, 0), (2, 1), (2, 2), (3, 0), (3, 1), (3, 2), (4, 0), (4, 1), (4, 2)]\n" 44 | ] 45 | } 46 | ], 47 | "source": [ 48 | "# Or Comprehension using for loops\n", 49 | "l = []\n", 50 | "for x in range(5):\n", 51 | " for y in range(3):\n", 52 | " l.append((x,y))\n", 53 | "\n", 54 | "print(l)" 55 | ] 56 | }, 57 | { 58 | "cell_type": "code", 59 | "execution_count": 22, 60 | "metadata": { 61 | "collapsed": false 62 | }, 63 | "outputs": [ 64 | { 65 | "data": { 66 | "text/plain": [ 67 | "'[Fraction(1, 1), Fraction(51, 50), Fraction(51, 49), Fraction(17, 16), Fraction(51, 47), Fraction(51, 46), ...]'" 68 | ] 69 | }, 70 | "execution_count": 22, 71 | "metadata": {}, 72 | "output_type": "execute_result" 73 | } 74 | ], 75 | "source": [ 76 | "# Comprehension 2 using multiple lines\n", 77 | "from fractions import Fraction as f\n", 78 | "from reprlib import repr\n", 79 | "value = [f(x) / f(x-y)\n", 80 | " for x in range(100)\n", 81 | " if x > 50\n", 82 | " for y in range(100)\n", 83 | " if x - y != 0]\n", 84 | "\n", 85 | "repr(value)" 86 | ] 87 | }, 88 | { 89 | "cell_type": "code", 90 | "execution_count": 20, 91 | "metadata": { 92 | "collapsed": false 93 | }, 94 | "outputs": [ 95 | { 96 | "data": { 97 | "text/plain": [ 98 | "'[Fraction(1, 1), Fraction(51, 50), Fraction(51, 49), Fraction(17, 16), Fraction(51, 47), Fraction(51, 46), ...]'" 99 | ] 100 | }, 101 | "execution_count": 20, 102 | "metadata": {}, 103 | "output_type": "execute_result" 104 | } 105 | ], 106 | "source": [ 107 | "# Comprehension 2 as nested for loop\n", 108 | "# List from 50/50, 51/49, 52/48, ..., upto 99/1\n", 109 | "l = []\n", 110 | "for x in range(100):\n", 111 | " if x > 50:\n", 112 | " for y in range(100):\n", 113 | " if (x - y) != 0:\n", 114 | " l.append(f(x) / f(x-y))\n", 115 | "repr(l)" 116 | ] 117 | }, 118 | { 119 | "cell_type": "code", 120 | "execution_count": 26, 121 | "metadata": { 122 | "collapsed": false 123 | }, 124 | "outputs": [ 125 | { 126 | "data": { 127 | "text/plain": [ 128 | "'[(1, 0), (2, 0), (2, 1), (3, 0), (3, 1), (3, 2), ...]'" 129 | ] 130 | }, 131 | "execution_count": 26, 132 | "metadata": {}, 133 | "output_type": "execute_result" 134 | } 135 | ], 136 | "source": [ 137 | "# Comprehension 3 to create a triangle of co-ordinates\n", 138 | "l = [(x, y) for x in range(10) for y in range(x)]\n", 139 | "repr(l)" 140 | ] 141 | }, 142 | { 143 | "cell_type": "code", 144 | "execution_count": 28, 145 | "metadata": { 146 | "collapsed": false 147 | }, 148 | "outputs": [ 149 | { 150 | "data": { 151 | "text/plain": [ 152 | "'[(1, 0), (2, 0), (2, 1), (3, 0), (3, 1), (3, 2), ...]'" 153 | ] 154 | }, 155 | "execution_count": 28, 156 | "metadata": {}, 157 | "output_type": "execute_result" 158 | } 159 | ], 160 | "source": [ 161 | "# Comprehension 3 as for loop\n", 162 | "l = []\n", 163 | "for x in range(10):\n", 164 | " for y in range(x):\n", 165 | " l.append((x, y))\n", 166 | "\n", 167 | "repr(l)" 168 | ] 169 | }, 170 | { 171 | "cell_type": "markdown", 172 | "metadata": {}, 173 | "source": [ 174 | "### Nested comprehensions" 175 | ] 176 | }, 177 | { 178 | "cell_type": "code", 179 | "execution_count": 47, 180 | "metadata": { 181 | "collapsed": false 182 | }, 183 | "outputs": [ 184 | { 185 | "name": "stdout", 186 | "output_type": "stream", 187 | "text": [ 188 | "[[3],\n", 189 | " [3, 6],\n", 190 | " [3, 6, 9],\n", 191 | " [3, 6, 9, 12],\n", 192 | " [3, 6, 9, 12, 15],\n", 193 | " [3, 6, 9, 12, 15, 18],\n", 194 | " [3, 6, 9, 12, 15, 18, 21],\n", 195 | " [3, 6, 9, 12, 15, 18, 21, 24]]\n" 196 | ] 197 | } 198 | ], 199 | "source": [ 200 | "# Comprehension 4 for printing incrementing list of multiples of 3\n", 201 | "from pprint import pprint as pp\n", 202 | "res = [[y * 3 for y in range(1, x)] for x in range(2, 10)]\n", 203 | "pp(res)" 204 | ] 205 | }, 206 | { 207 | "cell_type": "code", 208 | "execution_count": 52, 209 | "metadata": { 210 | "collapsed": false 211 | }, 212 | "outputs": [ 213 | { 214 | "name": "stdout", 215 | "output_type": "stream", 216 | "text": [ 217 | "[[3],\n", 218 | " [3, 6],\n", 219 | " [3, 6, 9],\n", 220 | " [3, 6, 9, 12],\n", 221 | " [3, 6, 9, 12, 15],\n", 222 | " [3, 6, 9, 12, 15, 18],\n", 223 | " [3, 6, 9, 12, 15, 18, 21],\n", 224 | " [3, 6, 9, 12, 15, 18, 21, 24]]\n" 225 | ] 226 | } 227 | ], 228 | "source": [ 229 | "# Comprehenion 4 using for loops\n", 230 | "outer_list = []\n", 231 | "for x in range(2, 10):\n", 232 | " inner_list = []\n", 233 | " for y in range(1, x):\n", 234 | " inner_list.append(y * 3)\n", 235 | " outer_list.append(inner_list)\n", 236 | "pp(outer_list)" 237 | ] 238 | }, 239 | { 240 | "cell_type": "markdown", 241 | "metadata": {}, 242 | "source": [ 243 | "## map()\n", 244 | "Given a sequence, create another sequence by applying method on the first. \n", 245 | "map() Yields value and hence must be iterated using next()" 246 | ] 247 | }, 248 | { 249 | "cell_type": "code", 250 | "execution_count": 55, 251 | "metadata": { 252 | "collapsed": false 253 | }, 254 | "outputs": [ 255 | { 256 | "data": { 257 | "text/plain": [ 258 | "\"['d', 'e', 'f', 'g', 'h', 'i', ...]\"" 259 | ] 260 | }, 261 | "execution_count": 55, 262 | "metadata": {}, 263 | "output_type": "execute_result" 264 | } 265 | ], 266 | "source": [ 267 | "l = list(map(chr, [x for x in range(100, 150)]))\n", 268 | "repr(l)" 269 | ] 270 | }, 271 | { 272 | "cell_type": "markdown", 273 | "metadata": {}, 274 | "source": [ 275 | "## Using multiple sequence with map" 276 | ] 277 | }, 278 | { 279 | "cell_type": "code", 280 | "execution_count": 63, 281 | "metadata": { 282 | "collapsed": false 283 | }, 284 | "outputs": [], 285 | "source": [ 286 | "(x, y, z) = ([x for x in range(10)],\n", 287 | " [y * 3 for y in range(10)],\n", 288 | " [z * 5 for z in range(10)])" 289 | ] 290 | }, 291 | { 292 | "cell_type": "code", 293 | "execution_count": 64, 294 | "metadata": { 295 | "collapsed": false 296 | }, 297 | "outputs": [ 298 | { 299 | "name": "stdout", 300 | "output_type": "stream", 301 | "text": [ 302 | "[[0, 0, 0],\n", 303 | " [1, 3, 5],\n", 304 | " [2, 6, 10],\n", 305 | " [3, 9, 15],\n", 306 | " [4, 12, 20],\n", 307 | " [5, 15, 25],\n", 308 | " [6, 18, 30],\n", 309 | " [7, 21, 35],\n", 310 | " [8, 24, 40],\n", 311 | " [9, 27, 45]]\n" 312 | ] 313 | } 314 | ], 315 | "source": [ 316 | "lst = list(map(lambda x,y,z: [x, y, z], x, y, z))\n", 317 | "pp(lst)" 318 | ] 319 | }, 320 | { 321 | "cell_type": "code", 322 | "execution_count": 65, 323 | "metadata": { 324 | "collapsed": true 325 | }, 326 | "outputs": [], 327 | "source": [ 328 | "# However map stops when one of the list is exhausted\n", 329 | "(x, y, z) = ([x for x in range(10)],\n", 330 | " [y * 3 for y in range(12)],\n", 331 | " [z * 5 for z in range(15)])" 332 | ] 333 | }, 334 | { 335 | "cell_type": "code", 336 | "execution_count": 67, 337 | "metadata": { 338 | "collapsed": false 339 | }, 340 | "outputs": [ 341 | { 342 | "name": "stdout", 343 | "output_type": "stream", 344 | "text": [ 345 | "[[0, 0, 0],\n", 346 | " [1, 3, 5],\n", 347 | " [2, 6, 10],\n", 348 | " [3, 9, 15],\n", 349 | " [4, 12, 20],\n", 350 | " [5, 15, 25],\n", 351 | " [6, 18, 30],\n", 352 | " [7, 21, 35],\n", 353 | " [8, 24, 40],\n", 354 | " [9, 27, 45]]\n" 355 | ] 356 | } 357 | ], 358 | "source": [ 359 | "# lst is similar to previous mapped lst\n", 360 | "lst = list(map(lambda x,y,z: [x, y, z], x, y, z))\n", 361 | "pp(lst)" 362 | ] 363 | }, 364 | { 365 | "cell_type": "markdown", 366 | "metadata": {}, 367 | "source": [ 368 | "### Using map() as comprehensions" 369 | ] 370 | }, 371 | { 372 | "cell_type": "code", 373 | "execution_count": 77, 374 | "metadata": { 375 | "collapsed": false 376 | }, 377 | "outputs": [ 378 | { 379 | "name": "stdout", 380 | "output_type": "stream", 381 | "text": [ 382 | "[0, 1, 2, 3, 4]\n", 383 | "[0, 1, 2, 3, 4]\n" 384 | ] 385 | } 386 | ], 387 | "source": [ 388 | "# This \n", 389 | "lst = list(map(int, range(5)))\n", 390 | "print(lst)\n", 391 | "\n", 392 | "# is similar to \n", 393 | "lst = [x for x in range(5)]\n", 394 | "print(lst)" 395 | ] 396 | }, 397 | { 398 | "cell_type": "markdown", 399 | "metadata": {}, 400 | "source": [ 401 | "## filter()\n", 402 | "Given a single sequence, create a sequence which matches the value filtered by given function" 403 | ] 404 | }, 405 | { 406 | "cell_type": "code", 407 | "execution_count": 80, 408 | "metadata": { 409 | "collapsed": false 410 | }, 411 | "outputs": [ 412 | { 413 | "name": "stdout", 414 | "output_type": "stream", 415 | "text": [ 416 | "[0, 2, 4, 6, 8]\n" 417 | ] 418 | } 419 | ], 420 | "source": [ 421 | "even = list(filter(lambda x: x % 2 == 0, [x for x in range(10)]))\n", 422 | "print(even)" 423 | ] 424 | }, 425 | { 426 | "cell_type": "markdown", 427 | "metadata": {}, 428 | "source": [ 429 | "## functools.reduce()\n", 430 | "Accumulate a given sequence using a function \n", 431 | "Does not work on empty sequences\n", 432 | "Returns the only iterable if passed without evaluating\n" 433 | ] 434 | }, 435 | { 436 | "cell_type": "code", 437 | "execution_count": 82, 438 | "metadata": { 439 | "collapsed": true 440 | }, 441 | "outputs": [], 442 | "source": [ 443 | "from functools import reduce\n", 444 | "from operator import add" 445 | ] 446 | }, 447 | { 448 | "cell_type": "code", 449 | "execution_count": 83, 450 | "metadata": { 451 | "collapsed": false 452 | }, 453 | "outputs": [ 454 | { 455 | "data": { 456 | "text/plain": [ 457 | "15" 458 | ] 459 | }, 460 | "execution_count": 83, 461 | "metadata": {}, 462 | "output_type": "execute_result" 463 | } 464 | ], 465 | "source": [ 466 | "reduce(add, [1, 2, 3, 4, 5]) " 467 | ] 468 | }, 469 | { 470 | "cell_type": "code", 471 | "execution_count": 84, 472 | "metadata": { 473 | "collapsed": false 474 | }, 475 | "outputs": [ 476 | { 477 | "name": "stdout", 478 | "output_type": "stream", 479 | "text": [ 480 | "15\n" 481 | ] 482 | } 483 | ], 484 | "source": [ 485 | "# Above using for loops\n", 486 | "num = [1, 2, 3, 4, 5]\n", 487 | "acc = 0\n", 488 | "for i in num:\n", 489 | " acc += i\n", 490 | "print(acc)" 491 | ] 492 | }, 493 | { 494 | "cell_type": "code", 495 | "execution_count": 90, 496 | "metadata": { 497 | "collapsed": false 498 | }, 499 | "outputs": [ 500 | { 501 | "name": "stdout", 502 | "output_type": "stream", 503 | "text": [ 504 | "0\n" 505 | ] 506 | } 507 | ], 508 | "source": [ 509 | "# reduce has optional initial value too\n", 510 | "try:\n", 511 | " x = reduce(add, [])\n", 512 | " print(x)\n", 513 | "except TypeError:\n", 514 | " x = reduce(add, [], 0)\n", 515 | " print(x)" 516 | ] 517 | } 518 | ], 519 | "metadata": { 520 | "kernelspec": { 521 | "display_name": "Python [conda root]", 522 | "language": "python", 523 | "name": "conda-root-py" 524 | }, 525 | "language_info": { 526 | "codemirror_mode": { 527 | "name": "ipython", 528 | "version": 3 529 | }, 530 | "file_extension": ".py", 531 | "mimetype": "text/x-python", 532 | "name": "python", 533 | "nbconvert_exporter": "python", 534 | "pygments_lexer": "ipython3", 535 | "version": "3.5.2" 536 | } 537 | }, 538 | "nbformat": 4, 539 | "nbformat_minor": 2 540 | } 541 | -------------------------------------------------------------------------------- /008_Iterables and Iteration/002_Iterables and Iteration.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## An example iterator\n", 8 | "An iterator is an object which follows the iterable protocol \n", 9 | "i.e implements the \\__iter\\__ method to self and the \\__next\\__ method" 10 | ] 11 | }, 12 | { 13 | "cell_type": "code", 14 | "execution_count": 20, 15 | "metadata": { 16 | "collapsed": true 17 | }, 18 | "outputs": [], 19 | "source": [ 20 | "class ExampleIterator:\n", 21 | " def __init__(self):\n", 22 | " self.index = 0\n", 23 | " self.data = [1, 2, 3]\n", 24 | " \n", 25 | " def __iter__(self):\n", 26 | " return self\n", 27 | " \n", 28 | " def __next__(self):\n", 29 | " if self.index >= len(self.data):\n", 30 | " raise StopIteration('Reached End')\n", 31 | " \n", 32 | " result = self.data[self.index]\n", 33 | " self.index += 1\n", 34 | " return result" 35 | ] 36 | }, 37 | { 38 | "cell_type": "code", 39 | "execution_count": 21, 40 | "metadata": { 41 | "collapsed": true 42 | }, 43 | "outputs": [], 44 | "source": [ 45 | "e = ExampleIterator()" 46 | ] 47 | }, 48 | { 49 | "cell_type": "code", 50 | "execution_count": 22, 51 | "metadata": { 52 | "collapsed": false 53 | }, 54 | "outputs": [ 55 | { 56 | "data": { 57 | "text/plain": [ 58 | "1" 59 | ] 60 | }, 61 | "execution_count": 22, 62 | "metadata": {}, 63 | "output_type": "execute_result" 64 | } 65 | ], 66 | "source": [ 67 | "next(e)" 68 | ] 69 | }, 70 | { 71 | "cell_type": "code", 72 | "execution_count": 23, 73 | "metadata": { 74 | "collapsed": false 75 | }, 76 | "outputs": [ 77 | { 78 | "data": { 79 | "text/plain": [ 80 | "2" 81 | ] 82 | }, 83 | "execution_count": 23, 84 | "metadata": {}, 85 | "output_type": "execute_result" 86 | } 87 | ], 88 | "source": [ 89 | "next(e)" 90 | ] 91 | }, 92 | { 93 | "cell_type": "code", 94 | "execution_count": 24, 95 | "metadata": { 96 | "collapsed": false 97 | }, 98 | "outputs": [ 99 | { 100 | "data": { 101 | "text/plain": [ 102 | "3" 103 | ] 104 | }, 105 | "execution_count": 24, 106 | "metadata": {}, 107 | "output_type": "execute_result" 108 | } 109 | ], 110 | "source": [ 111 | "next(e)" 112 | ] 113 | }, 114 | { 115 | "cell_type": "code", 116 | "execution_count": 25, 117 | "metadata": { 118 | "collapsed": false 119 | }, 120 | "outputs": [ 121 | { 122 | "name": "stdout", 123 | "output_type": "stream", 124 | "text": [ 125 | "Reached End\n" 126 | ] 127 | } 128 | ], 129 | "source": [ 130 | "try:\n", 131 | " next(e)\n", 132 | "except StopIteration as e:\n", 133 | " print(e)" 134 | ] 135 | }, 136 | { 137 | "cell_type": "code", 138 | "execution_count": 26, 139 | "metadata": { 140 | "collapsed": false 141 | }, 142 | "outputs": [ 143 | { 144 | "name": "stdout", 145 | "output_type": "stream", 146 | "text": [ 147 | "1\n", 148 | "2\n", 149 | "3\n" 150 | ] 151 | } 152 | ], 153 | "source": [ 154 | "# Or using for loops\n", 155 | "for i in ExampleIterator():\n", 156 | " print(i)" 157 | ] 158 | }, 159 | { 160 | "cell_type": "markdown", 161 | "metadata": {}, 162 | "source": [ 163 | "## Creating an Iterable\n", 164 | "Iterables implements the \\__iter\\__ method" 165 | ] 166 | }, 167 | { 168 | "cell_type": "code", 169 | "execution_count": 27, 170 | "metadata": { 171 | "collapsed": true 172 | }, 173 | "outputs": [], 174 | "source": [ 175 | "class ExampleIterator:\n", 176 | " def __init__(self, data):\n", 177 | " self.index = 0\n", 178 | " self.data = data\n", 179 | " \n", 180 | " def __iter__(self):\n", 181 | " return self\n", 182 | " \n", 183 | " def __next__(self):\n", 184 | " if self.index >= len(self.data):\n", 185 | " raise StopIteration('Reached End')\n", 186 | " \n", 187 | " result = self.data[self.index]\n", 188 | " self.index += 1\n", 189 | " return result" 190 | ] 191 | }, 192 | { 193 | "cell_type": "code", 194 | "execution_count": 28, 195 | "metadata": { 196 | "collapsed": true 197 | }, 198 | "outputs": [], 199 | "source": [ 200 | "class ExampleIterable:\n", 201 | " def __init__(self):\n", 202 | " self.data = [1, 2, 3]\n", 203 | " \n", 204 | " def __iter__(self):\n", 205 | " return ExampleIterator(self.data)" 206 | ] 207 | }, 208 | { 209 | "cell_type": "code", 210 | "execution_count": 29, 211 | "metadata": { 212 | "collapsed": false 213 | }, 214 | "outputs": [ 215 | { 216 | "name": "stdout", 217 | "output_type": "stream", 218 | "text": [ 219 | "1\n", 220 | "2\n", 221 | "3\n" 222 | ] 223 | } 224 | ], 225 | "source": [ 226 | "for i in ExampleIterable():\n", 227 | " print(i)" 228 | ] 229 | }, 230 | { 231 | "cell_type": "markdown", 232 | "metadata": {}, 233 | "source": [ 234 | "### Or using the \\__getitem\\__" 235 | ] 236 | }, 237 | { 238 | "cell_type": "code", 239 | "execution_count": 30, 240 | "metadata": { 241 | "collapsed": true 242 | }, 243 | "outputs": [], 244 | "source": [ 245 | "class AlterIterable:\n", 246 | " def __init__(self):\n", 247 | " self.data = [1, 2, 3]\n", 248 | " \n", 249 | " def __getitem__(self, index):\n", 250 | " return self.data[index]" 251 | ] 252 | }, 253 | { 254 | "cell_type": "code", 255 | "execution_count": 32, 256 | "metadata": { 257 | "collapsed": false 258 | }, 259 | "outputs": [ 260 | { 261 | "name": "stdout", 262 | "output_type": "stream", 263 | "text": [ 264 | "1\n", 265 | "2\n", 266 | "3\n" 267 | ] 268 | } 269 | ], 270 | "source": [ 271 | "for i in AlterIterable():\n", 272 | " print(i)" 273 | ] 274 | }, 275 | { 276 | "cell_type": "markdown", 277 | "metadata": {}, 278 | "source": [ 279 | "## Using the iter() method" 280 | ] 281 | }, 282 | { 283 | "cell_type": "code", 284 | "execution_count": 33, 285 | "metadata": { 286 | "collapsed": true 287 | }, 288 | "outputs": [], 289 | "source": [ 290 | "from datetime import datetime as d" 291 | ] 292 | }, 293 | { 294 | "cell_type": "code", 295 | "execution_count": 34, 296 | "metadata": { 297 | "collapsed": true 298 | }, 299 | "outputs": [], 300 | "source": [ 301 | "infinite_dates = iter(d.now, None)" 302 | ] 303 | }, 304 | { 305 | "cell_type": "code", 306 | "execution_count": 36, 307 | "metadata": { 308 | "collapsed": false 309 | }, 310 | "outputs": [ 311 | { 312 | "data": { 313 | "text/plain": [ 314 | "datetime.datetime(2017, 2, 25, 2, 6, 18, 52234)" 315 | ] 316 | }, 317 | "execution_count": 36, 318 | "metadata": {}, 319 | "output_type": "execute_result" 320 | } 321 | ], 322 | "source": [ 323 | "next(infinite_dates)" 324 | ] 325 | }, 326 | { 327 | "cell_type": "code", 328 | "execution_count": 38, 329 | "metadata": { 330 | "collapsed": false 331 | }, 332 | "outputs": [ 333 | { 334 | "data": { 335 | "text/plain": [ 336 | "datetime.datetime(2017, 2, 25, 2, 6, 56, 346451)" 337 | ] 338 | }, 339 | "execution_count": 38, 340 | "metadata": {}, 341 | "output_type": "execute_result" 342 | } 343 | ], 344 | "source": [ 345 | "next(infinite_dates)" 346 | ] 347 | }, 348 | { 349 | "cell_type": "code", 350 | "execution_count": 39, 351 | "metadata": { 352 | "collapsed": false 353 | }, 354 | "outputs": [ 355 | { 356 | "data": { 357 | "text/plain": [ 358 | "datetime.datetime(2017, 2, 25, 2, 7, 4, 380113)" 359 | ] 360 | }, 361 | "execution_count": 39, 362 | "metadata": {}, 363 | "output_type": "execute_result" 364 | } 365 | ], 366 | "source": [ 367 | "next(infinite_dates)" 368 | ] 369 | }, 370 | { 371 | "cell_type": "code", 372 | "execution_count": null, 373 | "metadata": { 374 | "collapsed": true 375 | }, 376 | "outputs": [], 377 | "source": [] 378 | } 379 | ], 380 | "metadata": { 381 | "kernelspec": { 382 | "display_name": "Python [conda root]", 383 | "language": "python", 384 | "name": "conda-root-py" 385 | }, 386 | "language_info": { 387 | "codemirror_mode": { 388 | "name": "ipython", 389 | "version": 3 390 | }, 391 | "file_extension": ".py", 392 | "mimetype": "text/x-python", 393 | "name": "python", 394 | "nbconvert_exporter": "python", 395 | "pygments_lexer": "ipython3", 396 | "version": "3.5.2" 397 | } 398 | }, 399 | "nbformat": 4, 400 | "nbformat_minor": 2 401 | } 402 | -------------------------------------------------------------------------------- /008_Iterables and Iteration/map_reduce/map_reduce.py: -------------------------------------------------------------------------------- 1 | '''Using map-reduce''' 2 | # -*- coding: utf-8 -*- 3 | 4 | from functools import reduce 5 | 6 | 7 | def count_words(doc): 8 | ''' Returns count for a string''' 9 | 10 | # Convert to lower case 11 | normalized_doc = ''.join(c.lower() if c.isalpha() else ' ' for c in doc) 12 | frequencies = {} 13 | # Split words 14 | for word in normalized_doc.split(): 15 | # frequencies.get(word, 0) == frequencies[word] if word in frequencies 16 | # else return 0 17 | frequencies[word] = frequencies.get(word, 0) + 1 18 | return frequencies 19 | 20 | DOCUMENTS = ['I was getting ready to be a threat', 21 | 'I was getting set for my', 22 | 'accidental suicide', 23 | 'the kind where no one dies'] 24 | 25 | # Map each string in DOCUMENTS to seperate dictionaries 26 | COUNTS = map(count_words, DOCUMENTS) 27 | 28 | 29 | def combine_words(first_dict, second_dict): 30 | '''Combine 2 dictionaries''' 31 | 32 | # Do a shallow copy of first_dict 33 | new_dict = first_dict.copy() 34 | for word, count in second_dict.items(): 35 | new_dict[word] = new_dict.get(word, 0) + count 36 | return new_dict 37 | 38 | # Combine all dictionaries 39 | TOTAL_COUNT = reduce(combine_words, COUNTS) 40 | 41 | print(TOTAL_COUNT) 42 | -------------------------------------------------------------------------------- /009_Inheritance and Subtype Polymorphism/001_Multiple Inheritance.ipynb: -------------------------------------------------------------------------------- 1 | { 2 | "cells": [ 3 | { 4 | "cell_type": "markdown", 5 | "metadata": {}, 6 | "source": [ 7 | "## Basic inheritance" 8 | ] 9 | }, 10 | { 11 | "cell_type": "code", 12 | "execution_count": 40, 13 | "metadata": { 14 | "collapsed": true 15 | }, 16 | "outputs": [], 17 | "source": [ 18 | "class Parent:\n", 19 | " def __init__(self):\n", 20 | " print('Parent Initializer')\n", 21 | " \n", 22 | " def func(self):\n", 23 | " print('Hello from Parent.func()')" 24 | ] 25 | }, 26 | { 27 | "cell_type": "code", 28 | "execution_count": 56, 29 | "metadata": { 30 | "collapsed": true 31 | }, 32 | "outputs": [], 33 | "source": [ 34 | "class Child(Parent):\n", 35 | " def __init__(self):\n", 36 | " super().__init__()\n", 37 | " print('Child Initializer')\n", 38 | " \n", 39 | " def func(self):\n", 40 | " super().func()\n", 41 | " print('Hello from Child.func()')" 42 | ] 43 | }, 44 | { 45 | "cell_type": "code", 46 | "execution_count": 57, 47 | "metadata": { 48 | "collapsed": false 49 | }, 50 | "outputs": [ 51 | { 52 | "name": "stdout", 53 | "output_type": "stream", 54 | "text": [ 55 | "Parent Initializer\n" 56 | ] 57 | } 58 | ], 59 | "source": [ 60 | "P1 = Parent()" 61 | ] 62 | }, 63 | { 64 | "cell_type": "code", 65 | "execution_count": 58, 66 | "metadata": { 67 | "collapsed": false 68 | }, 69 | "outputs": [ 70 | { 71 | "name": "stdout", 72 | "output_type": "stream", 73 | "text": [ 74 | "Hello from Parent.func()\n" 75 | ] 76 | } 77 | ], 78 | "source": [ 79 | "P1.func()" 80 | ] 81 | }, 82 | { 83 | "cell_type": "code", 84 | "execution_count": 61, 85 | "metadata": { 86 | "collapsed": false 87 | }, 88 | "outputs": [ 89 | { 90 | "name": "stdout", 91 | "output_type": "stream", 92 | "text": [ 93 | "Parent Initializer\n", 94 | "Child Initializer\n" 95 | ] 96 | } 97 | ], 98 | "source": [ 99 | "C1 = Child()" 100 | ] 101 | }, 102 | { 103 | "cell_type": "code", 104 | "execution_count": 62, 105 | "metadata": { 106 | "collapsed": false 107 | }, 108 | "outputs": [ 109 | { 110 | "name": "stdout", 111 | "output_type": "stream", 112 | "text": [ 113 | "Hello from Parent.func()\n", 114 | "Hello from Child.func()\n" 115 | ] 116 | } 117 | ], 118 | "source": [ 119 | "C1.func()" 120 | ] 121 | }, 122 | { 123 | "cell_type": "markdown", 124 | "metadata": {}, 125 | "source": [ 126 | "## A sorted list example" 127 | ] 128 | }, 129 | { 130 | "cell_type": "code", 131 | "execution_count": 20, 132 | "metadata": { 133 | "collapsed": true 134 | }, 135 | "outputs": [], 136 | "source": [ 137 | "from sorted_list import SimpleList, SortedList" 138 | ] 139 | }, 140 | { 141 | "cell_type": "code", 142 | "execution_count": 21, 143 | "metadata": { 144 | "collapsed": false 145 | }, 146 | "outputs": [], 147 | "source": [ 148 | "s = SortedList([21, 11, 1337, 42])" 149 | ] 150 | }, 151 | { 152 | "cell_type": "code", 153 | "execution_count": 22, 154 | "metadata": { 155 | "collapsed": false 156 | }, 157 | "outputs": [ 158 | { 159 | "name": "stdout", 160 | "output_type": "stream", 161 | "text": [ 162 | "SortedList([11, 21, 42, 1337])\n" 163 | ] 164 | } 165 | ], 166 | "source": [ 167 | "print(s)" 168 | ] 169 | }, 170 | { 171 | "cell_type": "code", 172 | "execution_count": 23, 173 | "metadata": { 174 | "collapsed": false 175 | }, 176 | "outputs": [ 177 | { 178 | "data": { 179 | "text/plain": [ 180 | "4" 181 | ] 182 | }, 183 | "execution_count": 23, 184 | "metadata": {}, 185 | "output_type": "execute_result" 186 | } 187 | ], 188 | "source": [ 189 | "len(s)" 190 | ] 191 | }, 192 | { 193 | "cell_type": "code", 194 | "execution_count": 24, 195 | "metadata": { 196 | "collapsed": true 197 | }, 198 | "outputs": [], 199 | "source": [ 200 | "s.add(33)" 201 | ] 202 | }, 203 | { 204 | "cell_type": "code", 205 | "execution_count": 25, 206 | "metadata": { 207 | "collapsed": false 208 | }, 209 | "outputs": [ 210 | { 211 | "name": "stdout", 212 | "output_type": "stream", 213 | "text": [ 214 | "SortedList([11, 21, 33, 42, 1337])\n" 215 | ] 216 | } 217 | ], 218 | "source": [ 219 | "print(s)" 220 | ] 221 | }, 222 | { 223 | "cell_type": "markdown", 224 | "metadata": {}, 225 | "source": [ 226 | "## Checking type of object using isinstance method" 227 | ] 228 | }, 229 | { 230 | "cell_type": "code", 231 | "execution_count": 26, 232 | "metadata": { 233 | "collapsed": false 234 | }, 235 | "outputs": [ 236 | { 237 | "data": { 238 | "text/plain": [ 239 | "True" 240 | ] 241 | }, 242 | "execution_count": 26, 243 | "metadata": {}, 244 | "output_type": "execute_result" 245 | } 246 | ], 247 | "source": [ 248 | "isinstance(21, int)" 249 | ] 250 | }, 251 | { 252 | "cell_type": "code", 253 | "execution_count": 27, 254 | "metadata": { 255 | "collapsed": false 256 | }, 257 | "outputs": [ 258 | { 259 | "data": { 260 | "text/plain": [ 261 | "True" 262 | ] 263 | }, 264 | "execution_count": 27, 265 | "metadata": {}, 266 | "output_type": "execute_result" 267 | } 268 | ], 269 | "source": [ 270 | "isinstance(s, SortedList)" 271 | ] 272 | }, 273 | { 274 | "cell_type": "code", 275 | "execution_count": 28, 276 | "metadata": { 277 | "collapsed": false 278 | }, 279 | "outputs": [ 280 | { 281 | "data": { 282 | "text/plain": [ 283 | "True" 284 | ] 285 | }, 286 | "execution_count": 28, 287 | "metadata": {}, 288 | "output_type": "execute_result" 289 | } 290 | ], 291 | "source": [ 292 | "isinstance(s, SimpleList)" 293 | ] 294 | }, 295 | { 296 | "cell_type": "code", 297 | "execution_count": 30, 298 | "metadata": { 299 | "collapsed": false 300 | }, 301 | "outputs": [ 302 | { 303 | "data": { 304 | "text/plain": [ 305 | "True" 306 | ] 307 | }, 308 | "execution_count": 30, 309 | "metadata": {}, 310 | "output_type": "execute_result" 311 | } 312 | ], 313 | "source": [ 314 | "isinstance ([], (tuple, dict, list)) # Will check if either of the type is true" 315 | ] 316 | }, 317 | { 318 | "cell_type": "markdown", 319 | "metadata": {}, 320 | "source": [ 321 | "## An IntList example" 322 | ] 323 | }, 324 | { 325 | "cell_type": "code", 326 | "execution_count": 44, 327 | "metadata": { 328 | "collapsed": true 329 | }, 330 | "outputs": [], 331 | "source": [ 332 | "from sorted_list import IntList" 333 | ] 334 | }, 335 | { 336 | "cell_type": "code", 337 | "execution_count": 45, 338 | "metadata": { 339 | "collapsed": false 340 | }, 341 | "outputs": [], 342 | "source": [ 343 | "i = IntList([12, 32, 19, 46])" 344 | ] 345 | }, 346 | { 347 | "cell_type": "code", 348 | "execution_count": 46, 349 | "metadata": { 350 | "collapsed": false 351 | }, 352 | "outputs": [ 353 | { 354 | "name": "stdout", 355 | "output_type": "stream", 356 | "text": [ 357 | "IntList([12, 32, 19, 46])\n" 358 | ] 359 | } 360 | ], 361 | "source": [ 362 | "print(i)" 363 | ] 364 | }, 365 | { 366 | "cell_type": "code", 367 | "execution_count": 47, 368 | "metadata": { 369 | "collapsed": false 370 | }, 371 | "outputs": [ 372 | { 373 | "data": { 374 | "text/plain": [ 375 | "4" 376 | ] 377 | }, 378 | "execution_count": 47, 379 | "metadata": {}, 380 | "output_type": "execute_result" 381 | } 382 | ], 383 | "source": [ 384 | "len(i)" 385 | ] 386 | }, 387 | { 388 | "cell_type": "code", 389 | "execution_count": 48, 390 | "metadata": { 391 | "collapsed": true 392 | }, 393 | "outputs": [], 394 | "source": [ 395 | "i.add(32)" 396 | ] 397 | }, 398 | { 399 | "cell_type": "code", 400 | "execution_count": 49, 401 | "metadata": { 402 | "collapsed": false 403 | }, 404 | "outputs": [ 405 | { 406 | "name": "stdout", 407 | "output_type": "stream", 408 | "text": [ 409 | "IntList([12, 32, 19, 46, 32])\n" 410 | ] 411 | } 412 | ], 413 | "source": [ 414 | "print(i)" 415 | ] 416 | }, 417 | { 418 | "cell_type": "markdown", 419 | "metadata": {}, 420 | "source": [ 421 | "## Using issubclass" 422 | ] 423 | }, 424 | { 425 | "cell_type": "code", 426 | "execution_count": 50, 427 | "metadata": { 428 | "collapsed": true 429 | }, 430 | "outputs": [], 431 | "source": [ 432 | "class ASimpleIntClass(int): pass" 433 | ] 434 | }, 435 | { 436 | "cell_type": "code", 437 | "execution_count": 51, 438 | "metadata": { 439 | "collapsed": true 440 | }, 441 | "outputs": [], 442 | "source": [ 443 | "class ASpIntClass(ASimpleIntClass): pass" 444 | ] 445 | }, 446 | { 447 | "cell_type": "code", 448 | "execution_count": 52, 449 | "metadata": { 450 | "collapsed": false 451 | }, 452 | "outputs": [ 453 | { 454 | "data": { 455 | "text/plain": [ 456 | "True" 457 | ] 458 | }, 459 | "execution_count": 52, 460 | "metadata": {}, 461 | "output_type": "execute_result" 462 | } 463 | ], 464 | "source": [ 465 | "issubclass(ASpIntClass, ASimpleIntClass)" 466 | ] 467 | }, 468 | { 469 | "cell_type": "code", 470 | "execution_count": 53, 471 | "metadata": { 472 | "collapsed": false 473 | }, 474 | "outputs": [ 475 | { 476 | "data": { 477 | "text/plain": [ 478 | "True" 479 | ] 480 | }, 481 | "execution_count": 53, 482 | "metadata": {}, 483 | "output_type": "execute_result" 484 | } 485 | ], 486 | "source": [ 487 | "issubclass(ASpIntClass, int)" 488 | ] 489 | }, 490 | { 491 | "cell_type": "markdown", 492 | "metadata": {}, 493 | "source": [ 494 | "## Using the SortedIntClass" 495 | ] 496 | }, 497 | { 498 | "cell_type": "code", 499 | "execution_count": 54, 500 | "metadata": { 501 | "collapsed": true 502 | }, 503 | "outputs": [], 504 | "source": [ 505 | "from sorted_list import SortedIntList" 506 | ] 507 | }, 508 | { 509 | "cell_type": "code", 510 | "execution_count": 55, 511 | "metadata": { 512 | "collapsed": false 513 | }, 514 | "outputs": [ 515 | { 516 | "data": { 517 | "text/plain": [ 518 | "True" 519 | ] 520 | }, 521 | "execution_count": 55, 522 | "metadata": {}, 523 | "output_type": "execute_result" 524 | } 525 | ], 526 | "source": [ 527 | "issubclass(SortedIntList, SortedList)" 528 | ] 529 | }, 530 | { 531 | "cell_type": "code", 532 | "execution_count": 56, 533 | "metadata": { 534 | "collapsed": false 535 | }, 536 | "outputs": [ 537 | { 538 | "data": { 539 | "text/plain": [ 540 | "True" 541 | ] 542 | }, 543 | "execution_count": 56, 544 | "metadata": {}, 545 | "output_type": "execute_result" 546 | } 547 | ], 548 | "source": [ 549 | "issubclass(SortedIntList, IntList)" 550 | ] 551 | }, 552 | { 553 | "cell_type": "code", 554 | "execution_count": 57, 555 | "metadata": { 556 | "collapsed": true 557 | }, 558 | "outputs": [], 559 | "source": [ 560 | "s = SortedIntList([12, 13, 15, 14])" 561 | ] 562 | }, 563 | { 564 | "cell_type": "code", 565 | "execution_count": 58, 566 | "metadata": { 567 | "collapsed": false 568 | }, 569 | "outputs": [ 570 | { 571 | "name": "stdout", 572 | "output_type": "stream", 573 | "text": [ 574 | "SortedIntList([12, 13, 14, 15])\n" 575 | ] 576 | } 577 | ], 578 | "source": [ 579 | "print(s)" 580 | ] 581 | }, 582 | { 583 | "cell_type": "code", 584 | "execution_count": 60, 585 | "metadata": { 586 | "collapsed": false 587 | }, 588 | "outputs": [ 589 | { 590 | "name": "stdout", 591 | "output_type": "stream", 592 | "text": [ 593 | "IntList only supports integer values.\n" 594 | ] 595 | } 596 | ], 597 | "source": [ 598 | "try:\n", 599 | " s.add('42')\n", 600 | "except TypeError as e:\n", 601 | " print(e)" 602 | ] 603 | }, 604 | { 605 | "cell_type": "markdown", 606 | "metadata": {}, 607 | "source": [ 608 | "## Whose \\__init\\__ is called?" 609 | ] 610 | }, 611 | { 612 | "cell_type": "code", 613 | "execution_count": 61, 614 | "metadata": { 615 | "collapsed": true 616 | }, 617 | "outputs": [], 618 | "source": [ 619 | "# Consider base classes\n", 620 | "class BaseI:\n", 621 | " def __init__(self):\n", 622 | " print('Hi from Base-I')\n", 623 | " \n", 624 | "class BaseII:\n", 625 | " def __init__(self):\n", 626 | " print('Hi from Base-II')" 627 | ] 628 | }, 629 | { 630 | "cell_type": "code", 631 | "execution_count": 62, 632 | "metadata": { 633 | "collapsed": true 634 | }, 635 | "outputs": [], 636 | "source": [ 637 | "class SubI(BaseI, BaseII): pass" 638 | ] 639 | }, 640 | { 641 | "cell_type": "code", 642 | "execution_count": 64, 643 | "metadata": { 644 | "collapsed": false 645 | }, 646 | "outputs": [ 647 | { 648 | "name": "stdout", 649 | "output_type": "stream", 650 | "text": [ 651 | "Hi from Base-I\n" 652 | ] 653 | }, 654 | { 655 | "data": { 656 | "text/plain": [ 657 | "<__main__.SubI at 0x7f3e207d9160>" 658 | ] 659 | }, 660 | "execution_count": 64, 661 | "metadata": {}, 662 | "output_type": "execute_result" 663 | } 664 | ], 665 | "source": [ 666 | "SubI() # Calls first base class argument i.e BaseI" 667 | ] 668 | }, 669 | { 670 | "cell_type": "code", 671 | "execution_count": 65, 672 | "metadata": { 673 | "collapsed": true 674 | }, 675 | "outputs": [], 676 | "source": [ 677 | "class SubII(BaseII, BaseI): pass" 678 | ] 679 | }, 680 | { 681 | "cell_type": "code", 682 | "execution_count": 67, 683 | "metadata": { 684 | "collapsed": false 685 | }, 686 | "outputs": [ 687 | { 688 | "name": "stdout", 689 | "output_type": "stream", 690 | "text": [ 691 | "Hi from Base-II\n" 692 | ] 693 | }, 694 | { 695 | "data": { 696 | "text/plain": [ 697 | "<__main__.SubII at 0x7f3e207d9a90>" 698 | ] 699 | }, 700 | "execution_count": 67, 701 | "metadata": {}, 702 | "output_type": "execute_result" 703 | } 704 | ], 705 | "source": [ 706 | "SubII() # Calls first base class argument i.e BaseII" 707 | ] 708 | }, 709 | { 710 | "cell_type": "markdown", 711 | "metadata": {}, 712 | "source": [ 713 | "## Getting base classes using \\__bases\\__\n", 714 | "\\__bases\\__ is a tuple of the base classes" 715 | ] 716 | }, 717 | { 718 | "cell_type": "code", 719 | "execution_count": 68, 720 | "metadata": { 721 | "collapsed": false 722 | }, 723 | "outputs": [ 724 | { 725 | "data": { 726 | "text/plain": [ 727 | "(object,)" 728 | ] 729 | }, 730 | "execution_count": 68, 731 | "metadata": {}, 732 | "output_type": "execute_result" 733 | } 734 | ], 735 | "source": [ 736 | "SimpleList.__bases__" 737 | ] 738 | }, 739 | { 740 | "cell_type": "code", 741 | "execution_count": 69, 742 | "metadata": { 743 | "collapsed": false 744 | }, 745 | "outputs": [ 746 | { 747 | "data": { 748 | "text/plain": [ 749 | "(sorted_list.SimpleList,)" 750 | ] 751 | }, 752 | "execution_count": 69, 753 | "metadata": {}, 754 | "output_type": "execute_result" 755 | } 756 | ], 757 | "source": [ 758 | "SortedList.__bases__" 759 | ] 760 | }, 761 | { 762 | "cell_type": "code", 763 | "execution_count": 70, 764 | "metadata": { 765 | "collapsed": false 766 | }, 767 | "outputs": [ 768 | { 769 | "data": { 770 | "text/plain": [ 771 | "(sorted_list.IntList, sorted_list.SortedList)" 772 | ] 773 | }, 774 | "execution_count": 70, 775 | "metadata": {}, 776 | "output_type": "execute_result" 777 | } 778 | ], 779 | "source": [ 780 | "SortedIntList.__bases__" 781 | ] 782 | }, 783 | { 784 | "cell_type": "markdown", 785 | "metadata": {}, 786 | "source": [ 787 | "## MRO - Method Resolution Order\n", 788 | "MRO is ordering of inheritance graph of base classes which define similar methods" 789 | ] 790 | }, 791 | { 792 | "cell_type": "code", 793 | "execution_count": 71, 794 | "metadata": { 795 | "collapsed": false 796 | }, 797 | "outputs": [ 798 | { 799 | "data": { 800 | "text/plain": [ 801 | "(sorted_list.SimpleList, object)" 802 | ] 803 | }, 804 | "execution_count": 71, 805 | "metadata": {}, 806 | "output_type": "execute_result" 807 | } 808 | ], 809 | "source": [ 810 | "SimpleList.__mro__" 811 | ] 812 | }, 813 | { 814 | "cell_type": "code", 815 | "execution_count": 72, 816 | "metadata": { 817 | "collapsed": false 818 | }, 819 | "outputs": [ 820 | { 821 | "data": { 822 | "text/plain": [ 823 | "(sorted_list.SortedList, sorted_list.SimpleList, object)" 824 | ] 825 | }, 826 | "execution_count": 72, 827 | "metadata": {}, 828 | "output_type": "execute_result" 829 | } 830 | ], 831 | "source": [ 832 | "SortedList.__mro__" 833 | ] 834 | }, 835 | { 836 | "cell_type": "code", 837 | "execution_count": 73, 838 | "metadata": { 839 | "collapsed": false 840 | }, 841 | "outputs": [ 842 | { 843 | "data": { 844 | "text/plain": [ 845 | "(sorted_list.SortedIntList,\n", 846 | " sorted_list.IntList,\n", 847 | " sorted_list.SortedList,\n", 848 | " sorted_list.SimpleList,\n", 849 | " object)" 850 | ] 851 | }, 852 | "execution_count": 73, 853 | "metadata": {}, 854 | "output_type": "execute_result" 855 | } 856 | ], 857 | "source": [ 858 | "SortedIntList.__mro__" 859 | ] 860 | }, 861 | { 862 | "cell_type": "markdown", 863 | "metadata": {}, 864 | "source": [ 865 | "## The super() method\n", 866 | "Given an MRO and a class super() gives you an object which resolves methods using only the part of the MRO which comes __after__ the given class." 867 | ] 868 | }, 869 | { 870 | "cell_type": "markdown", 871 | "metadata": {}, 872 | "source": [ 873 | "super() returns a proxy object which routes method calls \n", 874 | "Bounded proxies are proxies to a specific class/instance \n", 875 | "Unbounded proxies are proxies not bound to a specific class/instance" 876 | ] 877 | }, 878 | { 879 | "cell_type": "markdown", 880 | "metadata": {}, 881 | "source": [ 882 | "### Using super() for class bound proxy\n", 883 | "`super(BaseClass, DerivedClass)`" 884 | ] 885 | }, 886 | { 887 | "cell_type": "code", 888 | "execution_count": 76, 889 | "metadata": { 890 | "collapsed": false 891 | }, 892 | "outputs": [], 893 | "source": [ 894 | "class BaseA:\n", 895 | " def __init__(self):\n", 896 | " self.func()\n", 897 | " \n", 898 | " def func():\n", 899 | " print('Hello from A')\n", 900 | "\n", 901 | "class BaseB(BaseA):\n", 902 | " def func():\n", 903 | " print('Hello from B')\n", 904 | " \n", 905 | "class BaseC(BaseA):\n", 906 | " def func():\n", 907 | " print('Hello from C')" 908 | ] 909 | }, 910 | { 911 | "cell_type": "code", 912 | "execution_count": 78, 913 | "metadata": { 914 | "collapsed": false 915 | }, 916 | "outputs": [], 917 | "source": [ 918 | "class DerivedI(BaseB, BaseC): pass\n", 919 | "\n", 920 | "class DerivedII(BaseC, BaseB): pass" 921 | ] 922 | }, 923 | { 924 | "cell_type": "code", 925 | "execution_count": 79, 926 | "metadata": { 927 | "collapsed": false 928 | }, 929 | "outputs": [ 930 | { 931 | "data": { 932 | "text/plain": [ 933 | "[__main__.DerivedI, __main__.BaseB, __main__.BaseC, __main__.BaseA, object]" 934 | ] 935 | }, 936 | "execution_count": 79, 937 | "metadata": {}, 938 | "output_type": "execute_result" 939 | } 940 | ], 941 | "source": [ 942 | "DerivedI.mro()" 943 | ] 944 | }, 945 | { 946 | "cell_type": "code", 947 | "execution_count": 80, 948 | "metadata": { 949 | "collapsed": false 950 | }, 951 | "outputs": [ 952 | { 953 | "data": { 954 | "text/plain": [ 955 | "[__main__.DerivedII, __main__.BaseC, __main__.BaseB, __main__.BaseA, object]" 956 | ] 957 | }, 958 | "execution_count": 80, 959 | "metadata": {}, 960 | "output_type": "execute_result" 961 | } 962 | ], 963 | "source": [ 964 | "DerivedII.mro()" 965 | ] 966 | }, 967 | { 968 | "cell_type": "code", 969 | "execution_count": 82, 970 | "metadata": { 971 | "collapsed": false 972 | }, 973 | "outputs": [ 974 | { 975 | "data": { 976 | "text/plain": [ 977 | "" 978 | ] 979 | }, 980 | "execution_count": 82, 981 | "metadata": {}, 982 | "output_type": "execute_result" 983 | } 984 | ], 985 | "source": [ 986 | "super(BaseB, DerivedI) # A class bound proxy" 987 | ] 988 | }, 989 | { 990 | "cell_type": "code", 991 | "execution_count": 88, 992 | "metadata": { 993 | "collapsed": false 994 | }, 995 | "outputs": [ 996 | { 997 | "data": { 998 | "text/plain": [ 999 | "" 1000 | ] 1001 | }, 1002 | "execution_count": 88, 1003 | "metadata": {}, 1004 | "output_type": "execute_result" 1005 | } 1006 | ], 1007 | "source": [ 1008 | "super(BaseA, DerivedI)" 1009 | ] 1010 | }, 1011 | { 1012 | "cell_type": "code", 1013 | "execution_count": 86, 1014 | "metadata": { 1015 | "collapsed": false 1016 | }, 1017 | "outputs": [ 1018 | { 1019 | "name": "stdout", 1020 | "output_type": "stream", 1021 | "text": [ 1022 | "Hello from B\n" 1023 | ] 1024 | } 1025 | ], 1026 | "source": [ 1027 | "super(DerivedI, DerivedI).func()" 1028 | ] 1029 | }, 1030 | { 1031 | "cell_type": "code", 1032 | "execution_count": 83, 1033 | "metadata": { 1034 | "collapsed": false 1035 | }, 1036 | "outputs": [ 1037 | { 1038 | "name": "stdout", 1039 | "output_type": "stream", 1040 | "text": [ 1041 | "Hello from C\n" 1042 | ] 1043 | } 1044 | ], 1045 | "source": [ 1046 | "super(BaseB, DerivedI).func()" 1047 | ] 1048 | }, 1049 | { 1050 | "cell_type": "code", 1051 | "execution_count": 87, 1052 | "metadata": { 1053 | "collapsed": false 1054 | }, 1055 | "outputs": [ 1056 | { 1057 | "name": "stdout", 1058 | "output_type": "stream", 1059 | "text": [ 1060 | "Hello from A\n" 1061 | ] 1062 | } 1063 | ], 1064 | "source": [ 1065 | "super(BaseC, DerivedI).func()" 1066 | ] 1067 | }, 1068 | { 1069 | "cell_type": "code", 1070 | "execution_count": 92, 1071 | "metadata": { 1072 | "collapsed": false 1073 | }, 1074 | "outputs": [ 1075 | { 1076 | "name": "stdout", 1077 | "output_type": "stream", 1078 | "text": [ 1079 | "'super' object has no attribute 'func'\n" 1080 | ] 1081 | } 1082 | ], 1083 | "source": [ 1084 | "try:\n", 1085 | " super(BaseA, DerivedI).func()\n", 1086 | "except AttributeError as attr_e:\n", 1087 | " print(attr_e)" 1088 | ] 1089 | }, 1090 | { 1091 | "cell_type": "markdown", 1092 | "metadata": {}, 1093 | "source": [ 1094 | "### Using super for instance bound proxy" 1095 | ] 1096 | }, 1097 | { 1098 | "cell_type": "code", 1099 | "execution_count": 93, 1100 | "metadata": { 1101 | "collapsed": true 1102 | }, 1103 | "outputs": [], 1104 | "source": [ 1105 | "sil = SortedIntList([12, 13, 15, 14])" 1106 | ] 1107 | }, 1108 | { 1109 | "cell_type": "code", 1110 | "execution_count": 99, 1111 | "metadata": { 1112 | "collapsed": false 1113 | }, 1114 | "outputs": [ 1115 | { 1116 | "data": { 1117 | "text/plain": [ 1118 | "[sorted_list.SortedIntList,\n", 1119 | " sorted_list.IntList,\n", 1120 | " sorted_list.SortedList,\n", 1121 | " sorted_list.SimpleList,\n", 1122 | " object]" 1123 | ] 1124 | }, 1125 | "execution_count": 99, 1126 | "metadata": {}, 1127 | "output_type": "execute_result" 1128 | } 1129 | ], 1130 | "source": [ 1131 | "SortedIntList.mro()" 1132 | ] 1133 | }, 1134 | { 1135 | "cell_type": "code", 1136 | "execution_count": 102, 1137 | "metadata": { 1138 | "collapsed": false 1139 | }, 1140 | "outputs": [], 1141 | "source": [ 1142 | "super(SortedIntList, sil).add(4) # add() of IntList is called" 1143 | ] 1144 | }, 1145 | { 1146 | "cell_type": "code", 1147 | "execution_count": 105, 1148 | "metadata": { 1149 | "collapsed": false 1150 | }, 1151 | "outputs": [], 1152 | "source": [ 1153 | "super(SortedList, sil).add('4') # Works because add() method of SimpleList is called" 1154 | ] 1155 | }, 1156 | { 1157 | "cell_type": "markdown", 1158 | "metadata": {}, 1159 | "source": [ 1160 | "### So how does that work" 1161 | ] 1162 | }, 1163 | { 1164 | "cell_type": "code", 1165 | "execution_count": null, 1166 | "metadata": { 1167 | "collapsed": true 1168 | }, 1169 | "outputs": [], 1170 | "source": [ 1171 | "from IPython.display import Image\n", 1172 | "Image" 1173 | ] 1174 | } 1175 | ], 1176 | "metadata": { 1177 | "kernelspec": { 1178 | "display_name": "Python [conda root]", 1179 | "language": "python", 1180 | "name": "conda-root-py" 1181 | }, 1182 | "language_info": { 1183 | "codemirror_mode": { 1184 | "name": "ipython", 1185 | "version": 3 1186 | }, 1187 | "file_extension": ".py", 1188 | "mimetype": "text/x-python", 1189 | "name": "python", 1190 | "nbconvert_exporter": "python", 1191 | "pygments_lexer": "ipython3", 1192 | "version": "3.5.2" 1193 | } 1194 | }, 1195 | "nbformat": 4, 1196 | "nbformat_minor": 2 1197 | } 1198 | -------------------------------------------------------------------------------- /009_Inheritance and Subtype Polymorphism/sorted_list.py: -------------------------------------------------------------------------------- 1 | '''Create a list class''' 2 | 3 | 4 | class SimpleList: 5 | '''The list base class''' 6 | 7 | def __init__(self, items): 8 | self._items = list(items) 9 | 10 | def add(self, item): 11 | '''Append to list''' 12 | self._items.append(item) 13 | 14 | def __getitem__(self, index): 15 | return self._items[index] 16 | 17 | def sort(self): 18 | '''Sort the list''' 19 | self._items.sort() 20 | 21 | def __len__(self): 22 | return len(self._items) 23 | 24 | def __repr__(self): 25 | return "SimpleList({!r})".format(self._items) 26 | 27 | 28 | class SortedList(SimpleList): 29 | '''Sorts the list after every method''' 30 | 31 | def __init__(self, items=[]): 32 | super().__init__(items) 33 | self.sort() 34 | 35 | def add(self, item): 36 | super().add(item) 37 | self.sort() 38 | 39 | def __repr__(self): 40 | return "SortedList({!r})".format(list(self)) 41 | 42 | 43 | class IntList(SimpleList): 44 | '''List of only integers''' 45 | 46 | def __init__(self, items=[]): 47 | for element in items: 48 | self._validate(element) 49 | super().__init__(items) 50 | 51 | @staticmethod 52 | def _validate(element): 53 | if not isinstance(element, int): 54 | raise TypeError('IntList only supports integer values.') 55 | 56 | def add(self, item): 57 | self._validate(item) 58 | super().add(item) 59 | 60 | def __repr__(self): 61 | return "IntList({!r})".format(list(self)) 62 | 63 | 64 | class SortedIntList(IntList, SortedList): 65 | 66 | def __repr__(self): 67 | return 'SortedIntList({!r})'.format(list(self)) 68 | -------------------------------------------------------------------------------- /009_Inheritance and Subtype Polymorphism/super.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/ArchKudo/Python-Beyond-the-Basics/beadbc7ad77a2b4480c44635f93fc7289f87fd1c/009_Inheritance and Subtype Polymorphism/super.png -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## Python Beyond the Basics 2 | Notes/ Programs based on Python Beyond the Basics by Smallshire, Robert and Bingham, Austin 3 | -------------------------------------------------------------------------------- /_config.yml: -------------------------------------------------------------------------------- 1 | theme: jekyll-theme-cayman --------------------------------------------------------------------------------