├── .gitignore ├── README.md ├── Tor Browser and Selenium ├── __init__.py └── test.py ├── __init__.py ├── ansible_learn ├── __init__.py └── app.py ├── asyncio_learn ├── __init__.py ├── al_call_at.py ├── al_call_later.py ├── al_call_soon.py ├── al_coroutine.py ├── al_coroutine_multi.py ├── al_coroutine_return.py ├── cors_client.py ├── cors_thread.py └── simple_httpd.py ├── celery_learn ├── __init__.py ├── app.py ├── celeryconfig.py ├── clr.py └── tasks.py ├── cmdb_magedu ├── cmdb_magedu │ ├── __init__.py │ ├── __pycache__ │ │ ├── __init__.cpython-36.pyc │ │ ├── settings.cpython-36.pyc │ │ ├── urls.cpython-36.pyc │ │ └── wsgi.cpython-36.pyc │ ├── settings.py │ ├── urls.py │ └── wsgi.py ├── db.sqlite3 ├── manage.py └── user │ ├── __pycache__ │ ├── __init__.cpython-36.pyc │ ├── admin.cpython-36.pyc │ ├── apps.cpython-36.pyc │ ├── models.cpython-36.pyc │ ├── urls.cpython-36.pyc │ └── views.cpython-36.pyc │ ├── admin.py │ ├── apps.py │ ├── migrations │ ├── 0001_initial.py │ └── __pycache__ │ │ ├── 0001_initial.cpython-36.pyc │ │ └── __init__.cpython-36.pyc │ ├── models.py │ ├── templates │ └── user │ │ ├── login.html │ │ └── users.html │ ├── tests.py │ ├── urls.py │ └── views.py ├── django_learn ├── django_learn │ ├── __init__.py │ ├── settings.py │ ├── urls.py │ └── wsgi.py ├── manage.py └── polls │ ├── __init__.py │ ├── admin.py │ ├── apps.py │ ├── migrations │ └── __init__.py │ ├── models.py │ ├── tests.py │ ├── urls.py │ └── views.py ├── es_learn ├── __init__.py └── app.py ├── exec_othermodule_main ├── __init__.py ├── another_module.py ├── app.py └── other_module.py ├── gitlearn └── flow.md ├── mini_apps ├── __init__.py ├── beikezhaofang.py ├── bookSpider.py ├── bqb.py ├── camera_monitor.py ├── captain_shield.py ├── change_win_pwd │ ├── __init__.py │ ├── client.py │ └── server.py ├── font │ ├── DejaVu Sans Mono for Powerline.ttf │ ├── Ubuntu Mono derivative Powerline.ttf │ └── simsun.ttc ├── graph.py ├── imdbtop250 │ ├── __init__.py │ └── imdbtop250.py ├── img │ ├── img.jpeg │ └── jgz.jpeg ├── jgz.py ├── lambda_ex.py ├── love_heart.py ├── love_heart2.py ├── lover7c.py ├── maze.py ├── mouse_keyboard_controller.py ├── progressbar │ ├── __init__.py │ ├── stdout.py │ └── use_tqdm.py ├── tar2zip │ ├── 1-2.tar.gz │ ├── 1-2.zip │ ├── 1.txt │ ├── 2.txt │ ├── __init__.py │ ├── helper.py │ ├── tar2zip.py │ └── tmp.txt ├── test_func.py ├── weibo_login.py ├── xzpq.py └── 生成的表情包.jpg ├── python_data_structure ├── __init__.py ├── algorithm │ ├── __init__.py │ ├── dct.py │ └── disorder.py ├── base_data_structure │ ├── __init__.py │ ├── advance_check_brackets.py │ ├── app.py │ ├── check_brackets.py │ ├── deque.py │ ├── devide_by2.py │ ├── joseph_question.py │ ├── plaindrome.py │ ├── postfix.py │ ├── printer_queue.py │ ├── queue.py │ ├── stack.py │ └── unorderlist_orderlist.py ├── graph │ ├── __init__.py │ ├── bfs.py │ ├── graphs.py │ └── word_ladder.py ├── recursion │ ├── Sierpinski.py │ ├── __init__.py │ ├── change_coins.py │ ├── int2str.py │ ├── maze.py │ ├── maze_sample.txt │ ├── tower.py │ ├── tree.py │ └── visualization.py ├── sort_find │ ├── __init__.py │ ├── bubble_sort.py │ ├── hash_find.py │ ├── insert_sort.py │ ├── merge_sort.py │ ├── quick_sort.py │ ├── select_sort.py │ ├── sequential_search.py │ └── shell_sort.py └── tree │ ├── __init__.py │ ├── binary_heap.py │ ├── binary_tree.py │ ├── math_exp.py │ ├── tree_list.py │ └── tree_traverse.py ├── spider ├── __init__.py └── sexual_assault.py ├── tools └── __init__.py └── unit_test ├── __init__.py ├── app.py └── test2.py /.gitignore: -------------------------------------------------------------------------------- 1 | # By Miracle 2 | .idea/ 3 | .vscode/ 4 | **/.DS_Store 5 | 6 | # Byte-compiled / optimized / DLL files 7 | __pycache__/ 8 | *.py[cod] 9 | *$py.class 10 | 11 | # C extensions 12 | *.so 13 | 14 | # Distribution / packaging 15 | .Python 16 | env/ 17 | build/ 18 | develop-eggs/ 19 | dist/ 20 | downloads/ 21 | eggs/ 22 | .eggs/ 23 | lib/ 24 | lib64/ 25 | parts/ 26 | sdist/ 27 | var/ 28 | wheels/ 29 | *.egg-info/ 30 | .installed.cfg 31 | *.egg 32 | 33 | # PyInstaller 34 | # Usually these files are written by a python script from a template 35 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 36 | *.manifest 37 | *.spec 38 | 39 | # Installer logs 40 | pip-log.txt 41 | pip-delete-this-directory.txt 42 | 43 | # Unit test / coverage reports 44 | htmlcov/ 45 | .tox/ 46 | .coverage 47 | .coverage.* 48 | .cache 49 | nosetests.xml 50 | coverage.xml 51 | *.cover 52 | .hypothesis/ 53 | 54 | # Translations 55 | *.mo 56 | *.pot 57 | 58 | # Django stuff: 59 | *.log 60 | local_settings.py 61 | 62 | # Flask stuff: 63 | instance/ 64 | .webassets-cache 65 | 66 | # Scrapy stuff: 67 | .scrapy 68 | 69 | # Sphinx documentation 70 | docs/_build/ 71 | 72 | # PyBuilder 73 | target/ 74 | 75 | # Jupyter Notebook 76 | .ipynb_checkpoints 77 | 78 | # pyenv 79 | .python-version 80 | 81 | # celery beat schedule file 82 | celerybeat-schedule 83 | 84 | # SageMath parsed files 85 | *.sage.py 86 | 87 | # dotenv 88 | .env 89 | 90 | # virtualenv 91 | .venv 92 | venv/ 93 | ENV/ 94 | 95 | # Spyder project settings 96 | .spyderproject 97 | .spyproject 98 | 99 | # Rope project settings 100 | .ropeproject 101 | 102 | # mkdocs documentation 103 | /site 104 | 105 | # mypy 106 | .mypy_cache/ 107 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Exercises 2 | 3 | > Some exercises include: DB, tools, algorithm, apps, etc. 4 | 5 | -------------------------------------------------------------------------------- /Tor Browser and Selenium/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/5/31 上午7:32 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /Tor Browser and Selenium/test.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/5/31 上午7:39 4 | # @Author : MiracleYoung 5 | # @File : test.py 6 | 7 | import unittest 8 | from time import sleep 9 | from tbselenium.tbdriver import TorBrowserDriver 10 | 11 | 12 | class TestSite(unittest.TestCase): 13 | def setUp(self): 14 | # Point the path to the tor-browser_en-US directory in your system 15 | tbpath = '/home/kdas/.local/tbb/tor-browser_en-US/' 16 | self.driver = TorBrowserDriver(tbpath, tbb_logfile_path='test.log') 17 | self.url = "https://check.torproject.org" 18 | 19 | def tearDown(self): 20 | # We want the browser to close at the end of each test. 21 | self.driver.close() 22 | 23 | def test_available(self): 24 | self.driver.load_url(self.url) 25 | # Find the element for success 26 | element = self.driver.find_element_by_class_name('on') 27 | self.assertEqual(str.strip(element.text), 28 | "Congratulations. This browser is configured to use Tor.") 29 | sleep(2) # So that we can see the page 30 | 31 | 32 | if __name__ == '__main__': 33 | unittest.main() -------------------------------------------------------------------------------- /__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/5/18 4:06 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py 6 | 7 | __version__ = '0.0.1' 8 | __author__ = 'Miracle Young' -------------------------------------------------------------------------------- /ansible_learn/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/4/18 2:48 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /ansible_learn/app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/4/18 2:52 PM 4 | # @Author : Miracle Young 5 | # @File : app.py 6 | 7 | #!/usr/bin/env python 8 | 9 | import json 10 | import shutil 11 | from collections import namedtuple 12 | from ansible.parsing.dataloader import DataLoader 13 | from ansible.vars.manager import VariableManager 14 | from ansible.inventory.manager import InventoryManager 15 | from ansible.playbook.play import Play 16 | from ansible.executor.task_queue_manager import TaskQueueManager 17 | from ansible.plugins.callback import CallbackBase 18 | import ansible.constants as C 19 | 20 | class ResultCallback(CallbackBase): 21 | """A sample callback plugin used for performing an action as results come in 22 | 23 | If you want to collect all results into a single object for processing at 24 | the end of the execution, look into utilizing the ``json`` callback plugin 25 | or writing your own custom callback plugin 26 | """ 27 | def v2_runner_on_ok(self, result, **kwargs): 28 | """Print a json representation of the result 29 | 30 | This method could store the result in an instance attribute for retrieval later 31 | """ 32 | host = result._host 33 | print(json.dumps({host.name: result._result}, indent=4)) 34 | 35 | # since API is constructed for CLI it expects certain options to always be set, named tuple 'fakes' the args parsing options object 36 | Options = namedtuple('Options', ['connection', 'module_path', 'forks', 'become', 'become_method', 'become_user', 'check', 'diff']) 37 | options = Options(connection='local', module_path=['/to/mymodules'], forks=10, become=None, become_method=None, become_user=None, check=False, diff=False) 38 | 39 | # initialize needed objects 40 | loader = DataLoader() # Takes care of finding and reading yaml, json and ini files 41 | passwords = dict(vault_pass='secret') 42 | 43 | # Instantiate our ResultCallback for handling results as they come in. Ansible expects this to be one of its main display outlets 44 | results_callback = ResultCallback() 45 | 46 | # create inventory, use path to host config file as source or hosts in a comma separated string 47 | inventory = InventoryManager(loader=loader, sources='localhost,') 48 | 49 | # variable manager takes care of merging all the different sources to give you a unifed view of variables available in each context 50 | variable_manager = VariableManager(loader=loader, inventory=inventory) 51 | 52 | # create datastructure that represents our play, including tasks, this is basically what our YAML loader does internally. 53 | play_source = dict( 54 | name = "Ansible Play", 55 | hosts = 'localhost', 56 | gather_facts = 'no', 57 | tasks = [ 58 | dict(action=dict(module='shell', args='ls'), register='shell_out'), 59 | dict(action=dict(module='debug', args=dict(msg='{{shell_out.stdout}}'))) 60 | ] 61 | ) 62 | 63 | # Create play object, playbook objects use .load instead of init or new methods, 64 | # this will also automatically create the task objects from the info provided in play_source 65 | play = Play().load(play_source, variable_manager=variable_manager, loader=loader) 66 | 67 | # Run it - instantiate task queue manager, which takes care of forking and setting up all objects to iterate over host list and tasks 68 | tqm = None 69 | try: 70 | tqm = TaskQueueManager( 71 | inventory=inventory, 72 | variable_manager=variable_manager, 73 | loader=loader, 74 | options=options, 75 | passwords=passwords, 76 | stdout_callback=results_callback, # Use our custom callback instead of the ``default`` callback plugin, which prints to stdout 77 | ) 78 | result = tqm.run(play) # most interesting data for a play is actually sent to the callback's methods 79 | finally: 80 | # we always need to cleanup child procs and the structres we use to communicate with them 81 | if tqm is not None: 82 | tqm.cleanup() 83 | 84 | # Remove ansible tmpdir 85 | shutil.rmtree(C.DEFAULT_LOCAL_TMP, True) -------------------------------------------------------------------------------- /asyncio_learn/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/3/1 上午10:15 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /asyncio_learn/al_call_at.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/13 上午6:30 4 | # @Author : MiracleYoung 5 | # @File : al_call_at.py 6 | 7 | import asyncio 8 | import time 9 | 10 | 11 | def callback(n, loop): 12 | print(f'callback with {n} at {loop.time()}') 13 | 14 | async def main(loop): 15 | # 使用loop.time 而不是time和datetime模块 16 | now = loop.time() 17 | print(f'time模块的时间: {time.time()}') 18 | print(f'loop.time的时间: {now}') 19 | 20 | print('register callbacks') 21 | # 使用call_at指定当前时间后的0.2秒执行 22 | # 执行完了回掉callback 23 | # callback的n和loop参数 24 | loop.call_at(now + 0.2, callback, 1, loop) 25 | loop.call_at(now + 0.1, callback, 2, loop) 26 | # 和call_soon对比一下 27 | loop.call_soon(callback, 3, loop) 28 | 29 | await asyncio.sleep(1) 30 | 31 | 32 | event_loop = asyncio.get_event_loop() 33 | try: 34 | print('starting event_loop') 35 | event_loop.run_until_complete(main(event_loop)) 36 | finally: 37 | print('closing event_loop') 38 | event_loop.close() 39 | -------------------------------------------------------------------------------- /asyncio_learn/al_call_later.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/13 上午6:25 4 | # @Author : MiracleYoung 5 | # @File : al_call_later.py 6 | 7 | import asyncio 8 | 9 | def callback(n): 10 | print(f'callback with {n}') 11 | 12 | 13 | async def main(loop): 14 | print('register callbacks') 15 | # 延迟0.2秒执行 16 | # 执行完后调用callback函数 17 | # callback的参数n 18 | loop.call_later(0.2, callback, 1) 19 | loop.call_later(0.1, callback, 2) 20 | # 再来看下和call_soon的区别 21 | loop.call_soon(callback, 3) 22 | 23 | await asyncio.sleep(0.4) 24 | 25 | event_loop = asyncio.get_event_loop() 26 | try: 27 | print('starting event_loop') 28 | event_loop.run_until_complete(main(event_loop)) 29 | finally: 30 | print('closing event_loop') 31 | event_loop.close() -------------------------------------------------------------------------------- /asyncio_learn/al_call_soon.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/13 上午6:14 4 | # @Author : MiracleYoung 5 | # @File : al_call_soon.py 6 | 7 | import asyncio 8 | import functools 9 | 10 | # 下面我们将借助partial函数来说明如何使用关键字参数 11 | def callback(arg, *, kwarg='kwarg'): 12 | print(f'function callback with {arg} and {kwarg}') 13 | 14 | async def main(loop): 15 | print('register callbacks') 16 | # 还是通过get_event_loop 获取Eventloop 17 | loop.call_soon(callback, 'Miracle') 18 | # 使用partial函数,对kwarg参数进行控制 19 | wrapped = functools.partial(callback, kwarg='not kwarg') 20 | loop.call_soon(wrapped, '陈意涵') 21 | # 上一篇中说过的,await用于等待,sleep也不是time.sleep 22 | await asyncio.sleep(0.1) 23 | 24 | event_loop = asyncio.get_event_loop() 25 | try: 26 | print('starting event_loop') 27 | event_loop.run_until_complete(main(event_loop)) 28 | finally: 29 | print('closing event_loop') 30 | event_loop.close() 31 | -------------------------------------------------------------------------------- /asyncio_learn/al_coroutine.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/3/1 上午10:15 4 | # @Author : MiracleYoung 5 | # @File : app.py 6 | 7 | import asyncio 8 | 9 | # asyncio是Python 3.4版本引入的标准库,直接内置了对异步IO的支持。 10 | async def coroutine(): 11 | print('in coroutine') 12 | 13 | # asyncio的编程模型就是一个消息循环 14 | # 从asyncio模块中直接获取一个EventLoop的引用 15 | event_loop = asyncio.get_event_loop() 16 | try: 17 | print('starting coroutine') 18 | coro = coroutine() 19 | print('entering event loop') 20 | # 把需要执行的协程,这里也就是coroutine扔到EventLoop中执行 21 | event_loop.run_until_complete(coro) 22 | finally: 23 | print('closing event loop') 24 | event_loop.close() 25 | -------------------------------------------------------------------------------- /asyncio_learn/al_coroutine_multi.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/12 上午6:41 4 | # @Author : MiracleYoung 5 | # @File : al_coroutine_multi.py 6 | 7 | import asyncio 8 | 9 | # 函数1 10 | async def one(): 11 | print('in one') 12 | asyncio.sleep(1) 13 | print('one end') 14 | return 'one' 15 | 16 | # 函数2 17 | async def two(arg): 18 | print('in two') 19 | asyncio.sleep(1) 20 | print('two end') 21 | return 'two with arg {}'.format(arg) 22 | 23 | # 将作为coroutine 24 | async def outer(): 25 | print('in outer') 26 | print('waiting for one') 27 | # 等待函数1的返回值 28 | result1 = await one() 29 | print('waiting for two') 30 | # 等待函数2的返回值 31 | result2 = await two(result1) 32 | # 将2个结果一并返回 33 | return result1, result2 34 | 35 | 36 | event_loop = asyncio.get_event_loop() 37 | try: 38 | return_value = event_loop.run_until_complete(outer()) 39 | print(f'result value: {return_value}') 40 | finally: 41 | event_loop.close() 42 | -------------------------------------------------------------------------------- /asyncio_learn/al_coroutine_return.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/3/1 上午10:29 4 | # @Author : MiracleYoung 5 | # @File : app2.py 6 | 7 | 8 | import asyncio 9 | 10 | 11 | async def coroutine(): 12 | print('in coroutine') 13 | # 增加了一个返回值 14 | return 'result' 15 | 16 | 17 | event_loop = asyncio.get_event_loop() 18 | try: 19 | # 有了之前的基础,我们这里就不再单独获取coroutine的对象了 20 | # run_until_complete会返回coroutine的返回值 21 | return_value = event_loop.run_until_complete(coroutine()) 22 | print(f'it returned: {return_value}') 23 | finally: 24 | event_loop.close() 25 | -------------------------------------------------------------------------------- /asyncio_learn/cors_client.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/10/30 9:50 PM 4 | 5 | __author__ = 'Miracle' 6 | 7 | 8 | import requests 9 | 10 | def req_client(name): 11 | url = f'http://127.0.0.1:5000/' 12 | ret = requests.request('GET', url=url) 13 | return ret 14 | 15 | req_client('t1') -------------------------------------------------------------------------------- /asyncio_learn/cors_thread.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/10/30 9:32 PM 4 | 5 | __author__ = 'Miracle' 6 | 7 | import threading, time, logging 8 | from flask import Flask, Response 9 | import json 10 | 11 | app = Flask(__name__) 12 | logging.basicConfig(format='%(threadName)s %(message)s', level=logging.DEBUG) 13 | logger = logging.getLogger(__file__) 14 | 15 | 16 | @app.route('/', methods=['GET']) 17 | def th_fn(name): 18 | logger.info('receive response') 19 | time.sleep(10) 20 | # t = threading.Thread(target=lambda: print('after sleep 30s'), args=(), name=name, daemon=True) 21 | logger.info('after sleep 30s') 22 | # t.start() 23 | return Response(response='succeed') 24 | 25 | 26 | if __name__ == '__main__': 27 | app.run(host='0.0.0.0', port=5000, debug=True) 28 | 29 | # starts = [threading.Thread(target=th_fn, args=(f't{t}',), name=f'Thread-{t}', daemon=True) for t in range(2)] 30 | # for t in ts: 31 | # t.start() 32 | # 33 | # for t in ts: 34 | # t.join() 35 | # 36 | # print('end') 37 | -------------------------------------------------------------------------------- /asyncio_learn/simple_httpd.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/10/30 10:11 PM 4 | 5 | __author__ = 'Miracle' 6 | 7 | from wsgiref.simple_server import make_server 8 | 9 | import time, logging, threading 10 | 11 | logging.basicConfig(format='%(threadName)s %(message)s', level=logging.DEBUG) 12 | logger = logging.getLogger(__file__) 13 | 14 | # 创建一个服务器,IP地址为空,端口是8000,处理函数是application: 15 | 16 | def fn(): 17 | logger.info('threading start') 18 | time.sleep(10) 19 | logger.info('threading end.') 20 | 21 | def application(environ, start_response): 22 | logger.info('receive response') 23 | t = threading.Thread(target=fn, args=(), daemon=True) 24 | t.start() 25 | t.join() 26 | start_response('200 OK', [('Content-Type', 'text/html')]) 27 | logger.info('end response') 28 | return [b'

Hello, web!

'] 29 | 30 | 31 | httpd = make_server('', 5000, application) 32 | print("Serving HTTP on port 5000...") 33 | httpd.serve_forever() 34 | -------------------------------------------------------------------------------- /celery_learn/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/5/18 3:25 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /celery_learn/app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/5/18 3:52 PM 4 | # @Author : Miracle Young 5 | # @File : app.py 6 | 7 | # from celery import Celery, platforms 8 | # 9 | # platforms.C_FORCE_ROOT = True #加上这一行 10 | # 11 | 12 | from celery_learn.tasks import add 13 | 14 | add.delay(4, 4) -------------------------------------------------------------------------------- /celery_learn/celeryconfig.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/5/18 3:59 PM 4 | # @Author : Miracle Young 5 | # @File : celeryconfig.py 6 | 7 | 8 | BROKER_URL = 'redis://localhost' # 使用RabbitMQ作为消息代理 9 | 10 | CELERY_RESULT_BACKEND = 'redis://localhost' # 把任务结果存在了Redis 11 | 12 | CELERY_TASK_SERIALIZER = 'json' # 任务序列化和反序列化使用msgpack方案 13 | 14 | CELERY_RESULT_SERIALIZER = 'json' # 读取任务结果一般性能要求不高,所以使用了可读性更好的JSON 15 | 16 | CELERY_ACCEPT_CONTENT = ['json', 'msgpack'] # 指定接受的内容类型 17 | 18 | CELERY_TASK_RESULT_EXPIRES = 60 * 60 * 24 # 任务过期时间,不建议直接写86400,应该让这样的magic数字表述更明显 19 | 20 | # CELERY_ANNOTATIONS = { 21 | # 'tasks.add': {'rate_limit': '10/m'} 22 | # } 23 | -------------------------------------------------------------------------------- /celery_learn/clr.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/5/18 3:59 PM 4 | # @Author : Miracle Young 5 | # @File : celery.py 6 | 7 | 8 | -------------------------------------------------------------------------------- /celery_learn/tasks.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/5/18 3:59 PM 4 | # @Author : Miracle Young 5 | # @File : tasks.py 6 | 7 | from __future__ import absolute_import 8 | 9 | # from celery import Celery 10 | # 11 | # app = Celery('celery_learn', include=['celery_learn.tasks']) 12 | # 13 | # app.config_from_object('celery_learn.celeryconfig') 14 | # 15 | # if __name__ == '__main__': 16 | # app.start() 17 | 18 | 19 | from celery import Celery 20 | 21 | app = Celery('tasks', backend='redis://localhost', broker='redis://localhost') 22 | app.config_from_object('celeryconfig') 23 | 24 | @app.task 25 | def add(x, y): 26 | return x + y -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/__init__.py: -------------------------------------------------------------------------------- 1 | import pymysql 2 | pymysql.install_as_MySQLdb() -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/__pycache__/__init__.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/cmdb_magedu/__pycache__/__init__.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/__pycache__/settings.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/cmdb_magedu/__pycache__/settings.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/__pycache__/urls.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/cmdb_magedu/__pycache__/urls.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/__pycache__/wsgi.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/cmdb_magedu/__pycache__/wsgi.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/settings.py: -------------------------------------------------------------------------------- 1 | """ 2 | Django settings for cmdb_magedu project. 3 | 4 | Generated by 'django-admin startproject' using Django 1.11.7. 5 | 6 | For more information on this file, see 7 | https://docs.djangoproject.com/en/1.11/topics/settings/ 8 | 9 | For the full list of settings and their values, see 10 | https://docs.djangoproject.com/en/1.11/ref/settings/ 11 | """ 12 | 13 | import os 14 | 15 | # Build paths inside the project like this: os.path.join(BASE_DIR, ...) 16 | BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 17 | 18 | 19 | # Quick-start development settings - unsuitable for production 20 | # See https://docs.djangoproject.com/en/1.11/howto/deployment/checklist/ 21 | 22 | # SECURITY WARNING: keep the secret key used in production secret! 23 | SECRET_KEY = '@(7e)6#52y&(j1!nirw(0lyqx(wcwx9*w566@*h4l^wv4vaob6' 24 | 25 | # SECURITY WARNING: don't run with debug turned on in production! 26 | DEBUG = True 27 | 28 | ALLOWED_HOSTS = ['*'] 29 | 30 | 31 | # Application definition 32 | 33 | INSTALLED_APPS = [ 34 | 'django.contrib.admin', 35 | 'django.contrib.auth', 36 | 'django.contrib.contenttypes', 37 | 'django.contrib.sessions', 38 | 'django.contrib.messages', 39 | 'django.contrib.staticfiles', 40 | 41 | 'user.apps.UserConfig', 42 | ] 43 | 44 | MIDDLEWARE = [ 45 | 'django.middleware.security.SecurityMiddleware', 46 | 'django.contrib.sessions.middleware.SessionMiddleware', 47 | 'django.middleware.common.CommonMiddleware', 48 | 'django.middleware.csrf.CsrfViewMiddleware', 49 | 'django.contrib.auth.middleware.AuthenticationMiddleware', 50 | 'django.contrib.messages.middleware.MessageMiddleware', 51 | 'django.middleware.clickjacking.XFrameOptionsMiddleware', 52 | ] 53 | 54 | ROOT_URLCONF = 'cmdb_magedu.urls' 55 | 56 | TEMPLATES = [ 57 | { 58 | 'BACKEND': 'django.template.backends.django.DjangoTemplates', 59 | 'DIRS': [], 60 | 'APP_DIRS': True, 61 | 'OPTIONS': { 62 | 'context_processors': [ 63 | 'django.template.context_processors.debug', 64 | 'django.template.context_processors.request', 65 | 'django.contrib.auth.context_processors.auth', 66 | 'django.contrib.messages.context_processors.messages', 67 | ], 68 | }, 69 | }, 70 | ] 71 | 72 | WSGI_APPLICATION = 'cmdb_magedu.wsgi.application' 73 | 74 | 75 | # Database 76 | # https://docs.djangoproject.com/en/1.11/ref/settings/#databases 77 | 78 | DATABASES = { 79 | 'default': { 80 | 'ENGINE': 'django.db.backends.mysql', 81 | 'NAME': 'cmdb_magedu', 82 | 'HOST': '127.0.0.1', 83 | 'PORT': 3306, 84 | 'USER': 'root', 85 | 'PASSWORD': '', 86 | 'CHARSET': 'utf8', 87 | } 88 | } 89 | 90 | 91 | # Password validation 92 | # https://docs.djangoproject.com/en/1.11/ref/settings/#auth-password-validators 93 | 94 | AUTH_PASSWORD_VALIDATORS = [ 95 | { 96 | 'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator', 97 | }, 98 | { 99 | 'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator', 100 | }, 101 | { 102 | 'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator', 103 | }, 104 | { 105 | 'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator', 106 | }, 107 | ] 108 | 109 | 110 | # Internationalization 111 | # https://docs.djangoproject.com/en/1.11/topics/i18n/ 112 | 113 | LANGUAGE_CODE = 'en-us' 114 | 115 | TIME_ZONE = 'UTC' 116 | 117 | USE_I18N = True 118 | 119 | USE_L10N = True 120 | 121 | USE_TZ = True 122 | 123 | 124 | # Static files (CSS, JavaScript, Images) 125 | # https://docs.djangoproject.com/en/1.11/howto/static-files/ 126 | 127 | STATIC_URL = '/static/' 128 | -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/urls.py: -------------------------------------------------------------------------------- 1 | """cmdb_magedu URL Configuration 2 | 3 | The `urlpatterns` list routes URLs to views. For more information please see: 4 | https://docs.djangoproject.com/en/1.11/topics/http/urls/ 5 | Examples: 6 | Function views 7 | 1. Add an import: from my_app import views 8 | 2. Add a URL to urlpatterns: url(r'^$', views.home, name='home') 9 | Class-based views 10 | 1. Add an import: from other_app.views import Home 11 | 2. Add a URL to urlpatterns: url(r'^$', Home.as_view(), name='home') 12 | Including another URLconf 13 | 1. Import the include() function: from django.conf.urls import url, include 14 | 2. Add a URL to urlpatterns: url(r'^blog/', include('blog.urls')) 15 | """ 16 | from django.conf.urls import url, include 17 | from django.contrib import admin 18 | 19 | urlpatterns = [ 20 | url(r'^admin/', admin.site.urls), 21 | url(r'^user/', include('user.urls')), 22 | ] 23 | -------------------------------------------------------------------------------- /cmdb_magedu/cmdb_magedu/wsgi.py: -------------------------------------------------------------------------------- 1 | """ 2 | WSGI config for cmdb_magedu project. 3 | 4 | It exposes the WSGI callable as a module-level variable named ``application``. 5 | 6 | For more information on this file, see 7 | https://docs.djangoproject.com/en/1.11/howto/deployment/wsgi/ 8 | """ 9 | 10 | import os 11 | 12 | from django.core.wsgi import get_wsgi_application 13 | 14 | os.environ.setdefault("DJANGO_SETTINGS_MODULE", "cmdb_magedu.settings") 15 | 16 | application = get_wsgi_application() 17 | -------------------------------------------------------------------------------- /cmdb_magedu/db.sqlite3: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/db.sqlite3 -------------------------------------------------------------------------------- /cmdb_magedu/manage.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | import os 3 | import sys 4 | 5 | if __name__ == "__main__": 6 | os.environ.setdefault("DJANGO_SETTINGS_MODULE", "cmdb_magedu.settings") 7 | try: 8 | from django.core.management import execute_from_command_line 9 | except ImportError: 10 | # The above import may fail for some other reason. Ensure that the 11 | # issue is really that Django is missing to avoid masking other 12 | # exceptions on Python 2. 13 | try: 14 | import django 15 | except ImportError: 16 | raise ImportError( 17 | "Couldn't import Django. Are you sure it's installed and " 18 | "available on your PYTHONPATH environment variable? Did you " 19 | "forget to activate a virtual environment?" 20 | ) 21 | raise 22 | execute_from_command_line(sys.argv) 23 | -------------------------------------------------------------------------------- /cmdb_magedu/user/__pycache__/__init__.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/__pycache__/__init__.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/__pycache__/admin.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/__pycache__/admin.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/__pycache__/apps.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/__pycache__/apps.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/__pycache__/models.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/__pycache__/models.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/__pycache__/urls.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/__pycache__/urls.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/__pycache__/views.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/__pycache__/views.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | # Register your models here. 4 | -------------------------------------------------------------------------------- /cmdb_magedu/user/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class UserConfig(AppConfig): 5 | name = 'user' 6 | -------------------------------------------------------------------------------- /cmdb_magedu/user/migrations/0001_initial.py: -------------------------------------------------------------------------------- 1 | # -*- coding: utf-8 -*- 2 | # Generated by Django 1.11 on 2018-01-02 00:20 3 | from __future__ import unicode_literals 4 | 5 | from django.db import migrations, models 6 | 7 | 8 | class Migration(migrations.Migration): 9 | 10 | initial = True 11 | 12 | dependencies = [ 13 | ] 14 | 15 | operations = [ 16 | migrations.CreateModel( 17 | name='User', 18 | fields=[ 19 | ('id', models.AutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')), 20 | ('name', models.CharField(max_length=128)), 21 | ('age', models.IntegerField()), 22 | ('telephone', models.CharField(max_length=32)), 23 | ('email', models.EmailField(max_length=254)), 24 | ('register_time', models.DateTimeField(auto_now_add=True)), 25 | ('login_time', models.DateTimeField()), 26 | ], 27 | ), 28 | ] 29 | -------------------------------------------------------------------------------- /cmdb_magedu/user/migrations/__pycache__/0001_initial.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/migrations/__pycache__/0001_initial.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/migrations/__pycache__/__init__.cpython-36.pyc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/cmdb_magedu/user/migrations/__pycache__/__init__.cpython-36.pyc -------------------------------------------------------------------------------- /cmdb_magedu/user/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | # Create your models here. 4 | 5 | class User(models.Model): 6 | name = models.CharField(max_length=128) 7 | age = models.IntegerField() 8 | telephone = models.CharField(max_length=32) 9 | email = models.EmailField() 10 | register_time = models.DateTimeField(auto_now_add=True) 11 | login_time = models.DateTimeField() -------------------------------------------------------------------------------- /cmdb_magedu/user/templates/user/login.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 用户登录 6 | 7 | 8 | 9 | 用户登录: 10 | {% if errors %} 11 | {{ errors.0 }} 12 | {% for error in errors %} 13 | {{ error }} 14 | {% endfor %} 15 | {% endif %} 16 | 17 |
18 | {% csrf_token %} 19 | 用户名: 20 | 密码: 21 | 22 |
23 | 24 | 25 | -------------------------------------------------------------------------------- /cmdb_magedu/user/templates/user/users.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Title 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | {% for user in data %} 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 35 | 36 | {% endfor %} 37 | 38 | 39 |
用户名年龄电话号码邮箱地址注册时间登陆时间操作
{{ user.name }}{{ user.age }}{{ user.telephone }}{{ user.email }}{{ user.register_time }}{{ user.login_time }} 32 | 编辑 33 | 删除 34 |
40 | 41 | 42 | -------------------------------------------------------------------------------- /cmdb_magedu/user/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /cmdb_magedu/user/urls.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/1/2 上午6:50 4 | # @Author : MiracleYoung 5 | # @File : urls.py 6 | 7 | from django.conf.urls import url 8 | from . import views 9 | 10 | app_name = 'user' 11 | 12 | urlpatterns = [ 13 | url(r'^$', views.index, name='user'), 14 | url(r'^login/$', views.login, name='login'), 15 | url(r'^users/$', views.users, name='users'), 16 | 17 | ] -------------------------------------------------------------------------------- /cmdb_magedu/user/views.py: -------------------------------------------------------------------------------- 1 | from django.shortcuts import render, redirect 2 | from django.http import HttpResponse 3 | 4 | import time 5 | 6 | def index_v1(request): 7 | html = ''' 8 | 9 | 10 | ''' 11 | return HttpResponse(html) 12 | 13 | def index(request): 14 | print(request.GET, request.POST) 15 | context = { 16 | 'name': request.GET.get('name'), 17 | } 18 | return render(request, 'user/login.html', context) 19 | 20 | 21 | def login(request): 22 | print(request.GET, request.POST) 23 | name = request.POST.get('name', '') 24 | password = request.POST.get('password', '') 25 | if name == 'miracle' and password == 'cmdb': 26 | return redirect('user:users') 27 | else: 28 | context = {} 29 | context['name'] = name 30 | context['errors'] = ['用户名或密码错误'] 31 | return render(request, 'user/login.html', context) 32 | 33 | 34 | def users(request): 35 | context = { 36 | 'data': [ 37 | {'name': 'miracle', 'age': 18, 'telephone': 13916227150, 'email': 'miracle@gmail.com', 'register_time': time.time()}, 38 | ] 39 | } 40 | return render(request, 'user/users.html', context) -------------------------------------------------------------------------------- /django_learn/django_learn/__init__.py: -------------------------------------------------------------------------------- 1 | import pymysql 2 | 3 | pymysql.install_as_MySQLdb() -------------------------------------------------------------------------------- /django_learn/django_learn/settings.py: -------------------------------------------------------------------------------- 1 | """ 2 | Django settings for django_learn project. 3 | 4 | Generated by 'django-admin startproject' using Django 1.11. 5 | 6 | For more information on this file, see 7 | https://docs.djangoproject.com/en/1.11/topics/settings/ 8 | 9 | For the full list of settings and their values, see 10 | https://docs.djangoproject.com/en/1.11/ref/settings/ 11 | """ 12 | 13 | import os 14 | 15 | # Build paths inside the project like this: os.path.join(BASE_DIR, ...) 16 | BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__))) 17 | 18 | 19 | # Quick-start development settings - unsuitable for production 20 | # See https://docs.djangoproject.com/en/1.11/howto/deployment/checklist/ 21 | 22 | # SECURITY WARNING: keep the secret key used in production secret! 23 | SECRET_KEY = '$6cg8_l2g0^bn0$m@r8y7#$8i^l2-v72yzee6$22sho^77(!w^' 24 | 25 | # SECURITY WARNING: don't run with debug turned on in production! 26 | DEBUG = True 27 | 28 | ALLOWED_HOSTS = ['*'] 29 | 30 | 31 | # Application definition 32 | 33 | INSTALLED_APPS = [ 34 | 'django.contrib.admin', 35 | 'django.contrib.auth', 36 | 'django.contrib.contenttypes', 37 | 'django.contrib.sessions', 38 | 'django.contrib.messages', 39 | 'django.contrib.staticfiles', 40 | 41 | 'polls.apps.PollsConfig', 42 | ] 43 | 44 | MIDDLEWARE = [ 45 | 'django.middleware.security.SecurityMiddleware', 46 | 'django.contrib.sessions.middleware.SessionMiddleware', 47 | 'django.middleware.common.CommonMiddleware', 48 | 'django.middleware.csrf.CsrfViewMiddleware', 49 | 'django.contrib.auth.middleware.AuthenticationMiddleware', 50 | 'django.contrib.messages.middleware.MessageMiddleware', 51 | 'django.middleware.clickjacking.XFrameOptionsMiddleware', 52 | ] 53 | 54 | ROOT_URLCONF = 'django_learn.urls' 55 | 56 | TEMPLATES = [ 57 | { 58 | 'BACKEND': 'django.template.backends.django.DjangoTemplates', 59 | 'DIRS': [], 60 | 'APP_DIRS': True, 61 | 'OPTIONS': { 62 | 'context_processors': [ 63 | 'django.template.context_processors.debug', 64 | 'django.template.context_processors.request', 65 | 'django.contrib.auth.context_processors.auth', 66 | 'django.contrib.messages.context_processors.messages', 67 | ], 68 | }, 69 | }, 70 | ] 71 | 72 | WSGI_APPLICATION = 'django_learn.wsgi.application' 73 | 74 | 75 | # Database 76 | # https://docs.djangoproject.com/en/1.11/ref/settings/#databases 77 | 78 | DATABASES = { 79 | 'default': { 80 | 'ENGINE': 'django.db.backends.mysql', 81 | 'NAME': 'exercises', 82 | # 'HOST': '127.0.0.1', 83 | 'HOST': '127.0.0.1', 84 | 'PORT': 3306, 85 | 'USER': 'root', 86 | 'PASSWORD': '', 87 | 'CHARSET': 'utf8', 88 | } 89 | } 90 | 91 | 92 | # Password validation 93 | # https://docs.djangoproject.com/en/1.11/ref/settings/#auth-password-validators 94 | 95 | AUTH_PASSWORD_VALIDATORS = [ 96 | { 97 | 'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator', 98 | }, 99 | { 100 | 'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator', 101 | }, 102 | { 103 | 'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator', 104 | }, 105 | { 106 | 'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator', 107 | }, 108 | ] 109 | 110 | 111 | # Internationalization 112 | # https://docs.djangoproject.com/en/1.11/topics/i18n/ 113 | 114 | LANGUAGE_CODE = 'en-us' 115 | 116 | TIME_ZONE = 'UTC' 117 | 118 | USE_I18N = True 119 | 120 | USE_L10N = True 121 | 122 | USE_TZ = True 123 | 124 | 125 | # Static files (CSS, JavaScript, Images) 126 | # https://docs.djangoproject.com/en/1.11/howto/static-files/ 127 | 128 | STATIC_URL = '/static/' 129 | -------------------------------------------------------------------------------- /django_learn/django_learn/urls.py: -------------------------------------------------------------------------------- 1 | """django_learn URL Configuration 2 | 3 | The `urlpatterns` list routes URLs to views. For more information please see: 4 | https://docs.djangoproject.com/en/1.11/topics/http/urls/ 5 | Examples: 6 | Function views 7 | 1. Add an import: from my_app import views 8 | 2. Add a URL to urlpatterns: url(r'^$', views.home, name='home') 9 | Class-based views 10 | 1. Add an import: from other_app.views import Home 11 | 2. Add a URL to urlpatterns: url(r'^$', Home.as_view(), name='home') 12 | Including another URLconf 13 | 1. Import the include() function: from django.conf.urls import url, include 14 | 2. Add a URL to urlpatterns: url(r'^blog/', include('blog.urls')) 15 | """ 16 | from django.conf.urls import url, include 17 | from django.contrib import admin 18 | 19 | urlpatterns = [ 20 | url(r'^admin/', admin.site.urls), 21 | url(r'^polls/', include('polls.urls')), 22 | ] 23 | -------------------------------------------------------------------------------- /django_learn/django_learn/wsgi.py: -------------------------------------------------------------------------------- 1 | """ 2 | WSGI config for django_learn project. 3 | 4 | It exposes the WSGI callable as a module-level variable named ``application``. 5 | 6 | For more information on this file, see 7 | https://docs.djangoproject.com/en/1.11/howto/deployment/wsgi/ 8 | """ 9 | 10 | import os 11 | 12 | from django.core.wsgi import get_wsgi_application 13 | 14 | os.environ.setdefault("DJANGO_SETTINGS_MODULE", "django_learn.settings") 15 | 16 | application = get_wsgi_application() 17 | -------------------------------------------------------------------------------- /django_learn/manage.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | import os 3 | import sys 4 | 5 | if __name__ == "__main__": 6 | os.environ.setdefault("DJANGO_SETTINGS_MODULE", "django_learn.settings") 7 | try: 8 | from django.core.management import execute_from_command_line 9 | except ImportError: 10 | # The above import may fail for some other reason. Ensure that the 11 | # issue is really that Django is missing to avoid masking other 12 | # exceptions on Python 2. 13 | try: 14 | import django 15 | except ImportError: 16 | raise ImportError( 17 | "Couldn't import Django. Are you sure it's installed and " 18 | "available on your PYTHONPATH environment variable? Did you " 19 | "forget to activate a virtual environment?" 20 | ) 21 | raise 22 | execute_from_command_line(sys.argv) 23 | -------------------------------------------------------------------------------- /django_learn/polls/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/django_learn/polls/__init__.py -------------------------------------------------------------------------------- /django_learn/polls/admin.py: -------------------------------------------------------------------------------- 1 | from django.contrib import admin 2 | 3 | # Register your models here. 4 | -------------------------------------------------------------------------------- /django_learn/polls/apps.py: -------------------------------------------------------------------------------- 1 | from django.apps import AppConfig 2 | 3 | 4 | class PollsConfig(AppConfig): 5 | name = 'polls' 6 | -------------------------------------------------------------------------------- /django_learn/polls/migrations/__init__.py: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/django_learn/polls/migrations/__init__.py -------------------------------------------------------------------------------- /django_learn/polls/models.py: -------------------------------------------------------------------------------- 1 | from django.db import models 2 | 3 | # Create your models here. 4 | -------------------------------------------------------------------------------- /django_learn/polls/tests.py: -------------------------------------------------------------------------------- 1 | from django.test import TestCase 2 | 3 | # Create your tests here. 4 | -------------------------------------------------------------------------------- /django_learn/polls/urls.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 3/2/18 10:36 AM 4 | # @Author : Miracle Young 5 | # @File : urls.py 6 | 7 | from django.conf.urls import url 8 | 9 | from . import views 10 | 11 | urlpatterns = [ 12 | url(r'^$', views.index, name='index'), 13 | ] -------------------------------------------------------------------------------- /django_learn/polls/views.py: -------------------------------------------------------------------------------- 1 | from django.shortcuts import render 2 | 3 | # Create your views here. 4 | 5 | from django.contrib.auth.models import Group, User 6 | 7 | 8 | def index(request): 9 | 10 | u = User.objects.get(pk=1) 11 | 12 | ret = u.groups.add(1) 13 | 14 | print(ret) 15 | -------------------------------------------------------------------------------- /es_learn/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/28/18 11:03 AM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /es_learn/app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/28/18 11:05 AM 4 | # @Author : Miracle Young 5 | # @File : app.py 6 | 7 | 8 | -------------------------------------------------------------------------------- /exec_othermodule_main/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/25 上午6:22 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /exec_othermodule_main/another_module.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/25 上午6:26 4 | # @Author : MiracleYoung 5 | # @File : another_module.py 6 | 7 | import runpy 8 | 9 | runpy.run_path('app.py', run_name='__main__') -------------------------------------------------------------------------------- /exec_othermodule_main/app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/25 上午6:18 4 | # @Author : MiracleYoung 5 | # @File : exec_othermodule_main.py 6 | 7 | import sys 8 | 9 | 10 | def main(args): 11 | print(args) 12 | 13 | 14 | if __name__ == '__main__': 15 | print("执行如下代码 __name__ == '__main__'") 16 | # 参数随便指定即可 17 | main(sys.argv[1:]) 18 | -------------------------------------------------------------------------------- /exec_othermodule_main/other_module.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/25 上午6:22 4 | # @Author : MiracleYoung 5 | # @File : other_module.py 6 | 7 | import subprocess 8 | 9 | process = subprocess.run( 10 | ['python', 'app.py', 'miracle'], 11 | stdin=subprocess.PIPE, stdout=subprocess.PIPE 12 | ) 13 | print(process.stdout) 14 | -------------------------------------------------------------------------------- /gitlearn/flow.md: -------------------------------------------------------------------------------- 1 | ```flow 2 | s=>start: Start 3 | e=>end: End 4 | cond=>condition: Is Allowed? 5 | apply=>operation: Apply Register 6 | audit=>operation: Admin Audit 7 | form=>operation: Staff Get Authority and Fill out Form 8 | s->apply->audit->cond 9 | cond(yes)->form->e 10 | cond(no)->e 11 | ``` 12 | -------------------------------------------------------------------------------- /mini_apps/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/13 下午10:25 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /mini_apps/beikezhaofang.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/12/17 7:13 AM 4 | 5 | __author__ = 'Miracle' 6 | 7 | -------------------------------------------------------------------------------- /mini_apps/bookSpider.py: -------------------------------------------------------------------------------- 1 | import requests 2 | from lxml import etree 3 | import time 4 | import re 5 | import os 6 | import csv 7 | from fake_useragent import UserAgent 8 | 9 | # 实例化一个ua对象 10 | ua = UserAgent() 11 | 12 | 13 | class PythonBookSpider(object): 14 | """爬取京东商城前20页的Python书籍""" 15 | def __init__(self): 16 | self.base = "https://search.jd.com/Search?keyword=python&enc=utf-8&qrst=1&rt=1&stop=1&vt=2&wq=python&page={}" 17 | self.comment_url = "https://sclub.jd.com/comment/productCommentSummaries.action?referenceIds={}&" \ 18 | "callback=jQuery5954857&_={}" 19 | self.rank_url = "https://c.3.cn/book?skuId={}&cat=1713,3287,3797&area=1_72_2799_0&callback=book_jsonp_callback" 20 | self.headers = { 21 | "User-Agent": "Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.1 (KHTML, like Gecko) " 22 | "Chrome/22.0.1207.1 Safari/537.1", 23 | "authority": "search.jd.com" 24 | } 25 | 26 | def _send_request(self, url): 27 | """ 28 | 发送请求,获取响应 29 | :param url: 请求路径 30 | :return: 31 | """ 32 | # self.headers["User-Agent"] = random.choice(USER_AGENT_LIST) 33 | self.headers["User-Agent"] = ua.random 34 | time.sleep(0.5) 35 | response = requests.get(url=url, headers=self.headers, timeout=5) 36 | return response 37 | 38 | def send_request(self, url): 39 | """主要是对请求响应进行处理""" 40 | try: 41 | response = self._send_request(url) 42 | except Exception as e: 43 | print("request error: {}".format(e)) 44 | return None 45 | if response.status_code != 200: 46 | content = None 47 | else: 48 | content = response.content 49 | return content 50 | 51 | def get_comment_count(self, sku_id): 52 | """获取评论数""" 53 | print("comment url: {}".format(self.comment_url.format(sku_id, int(time.time())))) 54 | response = self.send_request(self.comment_url.format(sku_id, int(time.time()))) 55 | if not response: 56 | return "", "" 57 | # 响应的编码方式可以在响应中查看 58 | response = response.decode("GBK") 59 | good_rate = re.findall("\"GoodRate\":(\d\.\d+)", response)[0] if re.findall("\"GoodRate\":(\d\.\d+)", 60 | response) else "" 61 | commet_count = re.findall("\"CommentCount\":(\d+)", response)[0] if re.findall("\"CommentCount\":(\d+)", 62 | response) else "" 63 | # print(" good rate: {}".format(good_rate)) 64 | # print(" comment count: {}".format(commet_count)) 65 | return good_rate, commet_count 66 | 67 | def parse_book_rank(self, sku_id): 68 | """ 69 | 获取京东自营书籍销量排行榜名次 70 | :param sku_id: int 书籍的sku_id 71 | :return: 72 | """ 73 | # b'book_jsonp_callback({"yn":2,"rank":86,"ebookId":0})' 74 | response = self.send_request(self.rank_url.format(sku_id)) 75 | if not response: 76 | return False, None 77 | # print("book rank: {}".format(response)) 78 | # b_rank = eval(re.findall(r"\"rank:\d+\"", response.decode())[0]).split(":")[1] 79 | # re.findall(r"\"rank\":[\-|0-9][0-9]*", string) 80 | print("b_rank:{}".format(response.decode())) 81 | b_rank = re.findall(r"\"rank\":[\-|0-9][0-9]*", response.decode()) 82 | b_rank = b_rank[0].split(":")[1] if b_rank else "" 83 | 84 | return True, b_rank 85 | 86 | 87 | def save_book_info(self, books_list): 88 | """ 89 | 保存书籍信息 90 | :param files: 每一页的书籍信息 91 | """ 92 | if not os.path.exists("./PythonBookInfo.csv"): 93 | with open("./PythonBookInfo.csv", "a+", newline="") as file: 94 | writer = csv.writer(file) 95 | writer.writerow(["name", "price", "is_self_operated", "comment_counts", "good_comments_rate", 96 | "good_comments_rate", "sale_rank"]) 97 | with open("./PythonBookInfo.csv", "a+", newline="") as file: 98 | writer = csv.writer(file) 99 | for book_list in books_list: 100 | try: 101 | writer.writerows(book_list) 102 | except: 103 | continue 104 | 105 | def parse_index_page(self, response): 106 | """ 107 | 解析首页的界面信息 108 | :param response: type: str 搜索页面的响应 109 | :return: type: list 每一页的全部书籍相关信息 110 | """ 111 | index_selector = etree.HTML(response) 112 | books_list = index_selector.xpath('//div[@id="J_goodsList"]/ul/li') # 解析每一页的书籍列表 113 | py_bookinfo_list = [] 114 | for book in books_list: 115 | # 书籍详情地址 116 | b_url = book.xpath('.//div[@class="p-img"]/a/@href') 117 | # 图书价格 118 | b_price = book.xpath('.//div[@class="p-price"]//i/text()') 119 | # 卖家方式 120 | b_seller = book.xpath('//div[@class="p-icons"]/i[1]/text()') 121 | # 书名称 122 | b_name = book.xpath('.//div[@class="p-name"]//em') 123 | # print("b_name: {}".format(b_name[0].xpath("string(.)"))) 124 | b_name = [] if not b_name else b_name[0].xpath("string(.)").strip() 125 | # 书的评论数:通过js加载的 126 | sku_id = book.xpath('./@data-sku')[0] 127 | if not sku_id: 128 | continue 129 | good_rate, commet_count = self.get_comment_count(sku_id) 130 | if not all([b_url, b_price, good_rate, commet_count, b_name]): 131 | continue 132 | detail_url = "https:" + b_url[0] if not b_url[0].startswith("https") else b_url[0] 133 | # print("detail url:{}".format(detail_url)) 134 | # 如果是京东自营的话,在抓取对应的自营排名、出版社 135 | if b_seller[0] == "自营": 136 | # 获取书籍销售排行榜名次 137 | rank_response = self.parse_book_rank(sku_id) 138 | if not rank_response: 139 | continue 140 | b_rank = rank_response[1] 141 | b_seller = b_seller[0] 142 | # 获取书籍出版社 143 | # b_publisher = self.parse_detail_page(detail_url) 144 | else: 145 | b_rank = "" 146 | b_seller = "" 147 | py_bookinfo_list.append([[b_name, b_price[0], b_seller, commet_count, good_rate, b_rank, detail_url]]) 148 | return py_bookinfo_list 149 | 150 | def spider(self): 151 | """spider的主要逻辑业务""" 152 | for page in range(1, 21): 153 | # 1.请求搜索页,获取书籍列表页面信息,这里请求前20页 154 | first_response = self.send_request(self.base.format(2 * page - 1)) 155 | if not first_response: 156 | continue 157 | # 2.解析搜索页书籍的相关信息 158 | py_bookinfo_list = self.parse_index_page(first_response) 159 | if not py_bookinfo_list: 160 | continue 161 | # 3.保存爬取书籍信息 162 | self.save_book_info(py_bookinfo_list) 163 | print("第 {}页爬取完成".format(page)) 164 | 165 | print("抬头 望天") 166 | 167 | if __name__ == '__main__': 168 | py_spider = PythonBookSpider() 169 | py_spider.spider() 170 | 171 | -------------------------------------------------------------------------------- /mini_apps/bqb.py: -------------------------------------------------------------------------------- 1 | # 捂脸表情 2 | 3 | import turtle 4 | 5 | 6 | # 画指定的任意圆弧 7 | def arc(sa, ea, x, y, r): # start angle,end angle,circle center,radius 8 | turtle.penup() 9 | turtle.goto(x, y) 10 | turtle.setheading(0) 11 | turtle.left(sa) 12 | turtle.fd(r) 13 | turtle.pendown() 14 | turtle.left(90) 15 | turtle.circle(r, (ea - sa)) 16 | return turtle.position() 17 | 18 | 19 | turtle.hideturtle() 20 | # 画脸 21 | turtle.speed(5) 22 | turtle.setup(900, 600, 200, 200) 23 | turtle.pensize(5) 24 | turtle.right(90) 25 | turtle.penup() 26 | turtle.fd(100) 27 | turtle.left(90) 28 | turtle.pendown() 29 | turtle.begin_fill() 30 | turtle.pencolor("#B26A0F") # head side color 31 | turtle.circle(150) 32 | turtle.fillcolor("#F9E549") # face color 33 | turtle.end_fill() 34 | 35 | # 画嘴 36 | turtle.penup() 37 | turtle.goto(77, 20) 38 | turtle.pencolor("#744702") 39 | turtle.goto(0, 50) 40 | turtle.right(30) 41 | turtle.fd(110) 42 | turtle.right(90) 43 | turtle.pendown() 44 | turtle.begin_fill() 45 | turtle.fillcolor("#925902") # mouth color 46 | turtle.circle(-97, 160) 47 | turtle.goto(92, -3) 48 | turtle.end_fill() 49 | turtle.penup() 50 | turtle.goto(77, -25) 51 | # 画牙齿 52 | turtle.pencolor("white") 53 | turtle.begin_fill() 54 | turtle.fillcolor("white") 55 | turtle.goto(77, -24) 56 | turtle.goto(-81, 29) 57 | turtle.goto(-70, 43) 58 | turtle.goto(77, -8) 59 | turtle.end_fill() 60 | 61 | turtle.penup() 62 | turtle.goto(0, -100) 63 | turtle.setheading(0) 64 | turtle.pendown() 65 | 66 | # 画左边眼泪 67 | turtle.left(90) 68 | turtle.penup() 69 | turtle.fd(150) 70 | turtle.right(60) 71 | turtle.fd(-150) 72 | turtle.pendown() 73 | turtle.left(20) 74 | turtle.pencolor("#155F84") # tear side color 75 | turtle.fd(150) 76 | turtle.right(180) 77 | position1 = turtle.position() 78 | turtle.begin_fill() 79 | turtle.fillcolor("#7EB0C8") # tear color 80 | turtle.fd(150) 81 | turtle.right(20) 82 | turtle.left(270) 83 | turtle.circle(-150, 18) 84 | turtle.right(52) 85 | turtle.fd(110) 86 | position2 = turtle.position() 87 | turtle.goto(-33, 90) 88 | turtle.end_fill() 89 | # 画右边眼泪 90 | turtle.penup() 91 | turtle.goto(0, 0) 92 | turtle.setheading(0) 93 | turtle.left(90) 94 | turtle.fd(50) 95 | turtle.right(150) 96 | turtle.fd(150) 97 | turtle.left(150) 98 | turtle.fd(100) 99 | turtle.pendown() 100 | turtle.begin_fill() 101 | turtle.fd(-100) 102 | turtle.fillcolor("#7EB0C8") # tear color 103 | turtle.right(60) 104 | turtle.circle(150, 15) 105 | turtle.left(45) 106 | turtle.fd(66) 107 | turtle.goto(77, 20) 108 | turtle.end_fill() 109 | # 画眼睛 110 | turtle.penup() 111 | turtle.pencolor("#6C4E00") # eye color 112 | turtle.goto(-65, 75) 113 | turtle.setheading(0) 114 | turtle.left(27) 115 | turtle.fd(38) 116 | turtle.pendown() 117 | turtle.begin_fill() 118 | turtle.fillcolor("#6C4E00") # eye color 119 | turtle.left(90) 120 | turtle.circle(38, 86) 121 | turtle.goto(position2[0], position2[1]) 122 | turtle.goto(position1[0], position1[1]) 123 | turtle.end_fill() 124 | 125 | # 画手 126 | turtle.pencolor("#D57E18") # hand side color 127 | turtle.begin_fill() 128 | turtle.fillcolor("#EFBD3D") # hand color 129 | # 第一个手指 130 | arc(-110, 10, 110, -40, 30) 131 | turtle.circle(300, 35) 132 | turtle.circle(13, 120) 133 | turtle.setheading(-50) 134 | turtle.fd(20) 135 | turtle.setheading(130) 136 | # 第二个手指 137 | turtle.circle(200, 15) 138 | turtle.circle(12, 180) 139 | turtle.fd(40) 140 | turtle.setheading(137) 141 | # 第三个手指 142 | turtle.circle(200, 16) 143 | turtle.circle(12, 160) 144 | turtle.setheading(-35) 145 | turtle.fd(45) 146 | turtle.setheading(140) 147 | # 第四个手指 148 | turtle.circle(200, 13) 149 | turtle.circle(11, 160) 150 | turtle.setheading(-35) 151 | turtle.fd(40) 152 | turtle.setheading(145) 153 | # 第五个手指 154 | turtle.circle(200, 9) 155 | turtle.circle(10, 180) 156 | turtle.setheading(-31) 157 | turtle.fd(50) 158 | # 画最后手腕的部分 159 | turtle.setheading(-45) 160 | turtle.pensize(7) 161 | turtle.right(5) 162 | turtle.circle(180, 35) 163 | turtle.end_fill() 164 | turtle.begin_fill() 165 | turtle.setheading(-77) 166 | turtle.pensize(5) 167 | turtle.fd(50) 168 | turtle.left(-270) 169 | turtle.fd(7) 170 | turtle.pencolor("#EFBD3D") 171 | turtle.circle(30, 180) 172 | turtle.end_fill() 173 | # 测试 174 | # res=arc(70,220,90,50,300) 175 | # print(res[0],res[1]) 176 | 177 | turtle.done() 178 | 179 | 180 | ''' 181 | # 斜眼笑表情 182 | ''' 183 | import turtle as t 184 | 185 | # -------------脸 186 | t.setup(960, 959, 0, 0) 187 | t.color("orange") 188 | t.pensize("25") 189 | t.penup() 190 | t.goto(-300, 0) 191 | t.pendown() 192 | t.left(90) 193 | t.fillcolor("yellow") 194 | t.begin_fill() 195 | t.circle(-300) 196 | t.end_fill() 197 | 198 | # -----------嘴----------- 199 | t.penup() 200 | t.goto(-220, -10) 201 | t.seth(90) 202 | for i in range(90): 203 | t.pensize(4 + 0.15 * i) 204 | t.color("brown") 205 | t.pendown() 206 | t.circle(-220, -1) 207 | for i in range(90): 208 | t.pensize(17.5 - 0.15 * i) 209 | t.color("brown") 210 | t.pendown() 211 | t.circle(-220, -1) 212 | 213 | # ------------左眼--------------- 214 | t.penup() 215 | t.goto(-80, 150) 216 | t.color("orange") 217 | t.pensize("25") 218 | t.seth(90) 219 | t.pendown() 220 | t.left(50) 221 | t.circle(200, 80) 222 | t.seth(270) 223 | t.circle(200, 15) 224 | 225 | t.penup() 226 | t.goto(-70, 90) 227 | t.color("orange") 228 | t.pensize("25") 229 | t.seth(90) 230 | t.pendown() 231 | t.left(50) 232 | t.circle(200, 65) 233 | t.left(10) 234 | t.circle(200, 10) 235 | 236 | t.penup() 237 | t.goto(-70, 150) 238 | t.seth(270) 239 | t.pendown() 240 | t.circle(-200, 15) 241 | 242 | # -------------右眼---------------- 243 | 244 | 245 | t.penup() 246 | t.goto(70, 150) 247 | t.color("orange") 248 | t.pensize("25") 249 | t.seth(90) 250 | t.pendown() 251 | t.right(50) 252 | t.circle(-200, 80) 253 | t.seth(270) 254 | t.circle(-200, 15) 255 | 256 | t.penup() 257 | t.goto(70, 90) 258 | t.seth(90) 259 | t.pendown() 260 | t.right(50) 261 | t.circle(-200, 65) 262 | t.right(10) 263 | t.circle(200, 10) 264 | 265 | t.penup() 266 | t.goto(70, 150) 267 | t.seth(270) 268 | t.pendown() 269 | t.circle(200, 15) 270 | 271 | t.penup() 272 | t.pensize(5) 273 | t.color("black") 274 | t.goto(-300, 125) 275 | t.pendown() 276 | t.seth(0) 277 | t.fillcolor('black') 278 | t.begin_fill() 279 | t.circle(15, 360) 280 | t.end_fill() 281 | 282 | t.penup() 283 | t.pensize(5) 284 | t.color("black") 285 | t.goto(100, 120) 286 | t.pendown() 287 | t.seth(0) 288 | t.fillcolor('black') 289 | t.begin_fill() 290 | t.circle(15, 360) 291 | t.end_fill() 292 | 293 | # ----------左眉毛----------------- 294 | t.penup() 295 | t.goto(-70, 200) 296 | t.color("black") 297 | t.pensize("25") 298 | t.seth(90) 299 | t.pendown() 300 | t.left(30) 301 | t.circle(200, 60) 302 | 303 | # ----------右眉毛----------------- 304 | t.penup() 305 | t.goto(70, 200) 306 | t.color("black") 307 | t.pensize("25") 308 | t.seth(90) 309 | t.pendown() 310 | t.right(30) 311 | t.circle(-200, 60) 312 | 313 | # ---------左红------------------- 314 | t.penup() 315 | t.color("red") 316 | t.goto(150, 20) 317 | t.pendown() 318 | t.fillcolor("red") 319 | t.begin_fill() 320 | t.circle(20) 321 | t.end_fill() 322 | 323 | # ---------右红---------------- 324 | t.penup() 325 | t.color("red") 326 | t.goto(-180, 20) 327 | t.pendown() 328 | t.fillcolor("red") 329 | t.begin_fill() 330 | t.circle(20) 331 | t.end_fill() 332 | 333 | t.done() 334 | -------------------------------------------------------------------------------- /mini_apps/camera_monitor.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/7/21 下午11:40 4 | # @Author : MiracleYoung 5 | # @File : camera_monitor.py 6 | 7 | 8 | import cv2 9 | import dlib 10 | from subprocess import call 11 | from time import time 12 | 13 | FREQ = 5 14 | FACE_DETECTOR = dlib.get_frontal_face_detector() 15 | 16 | 17 | # macOS下可以使用AppleScript发送通知 18 | def notify(text, title): 19 | cmd = r'display notification "%s" with title "%s"' % (text, title) 20 | call(["osascript", "-e", cmd]) 21 | 22 | 23 | if __name__ == '__main__': 24 | # 初始化摄像头 25 | cap = cv2.VideoCapture(0) 26 | # 创建绘图窗口 27 | cv2.namedWindow('face') 28 | notify_time = 0 29 | while True: 30 | # 获取一帧 31 | ret, frame = cap.read() 32 | # 不需要太精细的图片 33 | frame = cv2.resize(frame, (320, 240)) 34 | # 探测人脸,可能有多个 35 | faces = FACE_DETECTOR(frame, 1) 36 | for face in faces: 37 | # 提取人脸部分 画个方框 38 | fimg = frame[face.top():face.bottom(), face.left():face.right()] # cv2.rectangle(frame, (face.left(), face.top()), (face.right(), face.bottom()), (255, 0, 0), 3) # 不超过FREQ秒一次的发提醒 if time() - notify_time > FREQ: notify(u'检测到人脸', u'注意') notify_time = time()# 画到窗口里# cv2.imshow('face', frame)# 按Q退出 if cv2.waitKey(500) & 0xff == ord('q'): break# 清理窗口 释放摄像头 # cv2.destroyAllWindows() cap.release() 39 | -------------------------------------------------------------------------------- /mini_apps/captain_shield.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/7/18 上午7:16 4 | # @Author : MiracleYoung 5 | # @File : captain_shield.py 6 | 7 | import turtle 8 | 9 | t = turtle.Turtle() 10 | 11 | 12 | def setpen(x, y): 13 | # 抬笔 14 | t.penup() 15 | # 移动画笔到(x, y) 16 | t.goto(x, y) 17 | # 落笔 18 | t.pendown() 19 | t.setheading(0) 20 | 21 | 22 | def circle(x, y, r, color): 23 | # 为了保证画出的圆够圆,所以我们把圆的边设置的多一些 24 | n = 36 25 | angle = 360 / n 26 | pi = 3.1415926 27 | # 周长 28 | c = 2 * pi * r 29 | # 每条边的长度 30 | l = c / n 31 | # 起始位置 32 | start_x = x - l / 2 33 | start_y = y + r 34 | # 移动画笔 35 | setpen(start_x, start_y) 36 | # 选择画笔颜色 37 | t.pencolor(color) 38 | # 选择背景色 39 | t.fillcolor(color) 40 | # 填充 41 | t.begin_fill() 42 | for i in range(n): 43 | t.forward(l) 44 | t.right(angle) 45 | t.end_fill() 46 | 47 | 48 | def five_star(l): 49 | setpen(0, 0) 50 | t.setheading(162) 51 | t.forward(150) 52 | t.setheading(0) 53 | t.fillcolor('WhiteSmoke') 54 | t.begin_fill() 55 | t.hideturtle() 56 | t.penup() 57 | for i in range(5): 58 | t.forward(l) 59 | t.right(144) 60 | t.end_fill() 61 | 62 | 63 | def sheild(): 64 | circle(0, 0, 300, 'red') 65 | circle(0, 0, 250, 'white') 66 | circle(0, 0, 200, 'red') 67 | circle(0, 0, 150, 'blue') 68 | five_star(284) 69 | 70 | 71 | if __name__ == '__main__': 72 | sheild() 73 | # 结束乌龟图 74 | turtle.done() 75 | -------------------------------------------------------------------------------- /mini_apps/change_win_pwd/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/1/28 5:18 AM 4 | 5 | __author__ = 'Miracle' -------------------------------------------------------------------------------- /mini_apps/change_win_pwd/client.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/1/28 5:18 AM 4 | 5 | __author__ = 'Miracle' 6 | 7 | import socket 8 | import getpass 9 | import subprocess 10 | import random 11 | import string 12 | 13 | # 我们使用socket与服务器进行交互,因为这个比较简单,否则server端还要写个接口 14 | client = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 15 | 16 | # 连接server端IP地址、端口,如果你是在家里的电脑,那你得去路由器上做个端口映射 17 | client.connect(('192.168.31.246', 8080)) 18 | 19 | # 获取计算机用户名 20 | user = getpass.getuser() 21 | 22 | # 生成a-zA-Z0-9的随机密码 23 | letters = string.ascii_letters + string.digits 24 | pwd = ''.join([random.choice(letters) for _ in range(8)]) 25 | 26 | # 控制windows cmd,并修改密码 27 | subprocess.Popen(['net', 'User', user, pwd]) 28 | 29 | # 通过socket 将密码发送给server端 30 | client.send(pwd.encode('utf-8')) 31 | 32 | msg = client.recv(1024) 33 | client.close() 34 | print(pwd) 35 | -------------------------------------------------------------------------------- /mini_apps/change_win_pwd/server.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/1/28 5:18 AM 4 | 5 | __author__ = 'Miracle' 6 | 7 | 8 | import socket 9 | 10 | # server端同样需要通过创建socket,来监听client请求 11 | server = socket.socket(socket.AF_INET, socket.SOCK_STREAM) 12 | 13 | # 这里和客户端不一样的是,使用的是bind,代表server端自己的ip port 14 | server.bind(('192.168.31.246', 8080)) 15 | 16 | # 这里的参数5 代表的是同时监听多少个客户端,如果超过5个,那么第6个客户端会出现响应等待,也就是卡在那了 17 | server.listen(5) 18 | 19 | print('starting....') 20 | # 创建socket连接后,会返回连接实例和地址 21 | conn, addr = server.accept() 22 | 23 | print(conn) 24 | print('client addr', addr) 25 | print('ready to recv the passwd...') 26 | 27 | while True: 28 | # 等待接受客户端发过来的信息 29 | client_msg = conn.recv(1024) 30 | print('client passwd changed: %s' % client_msg.decode()) 31 | 32 | # conn.close() 33 | # server.close() -------------------------------------------------------------------------------- /mini_apps/font/DejaVu Sans Mono for Powerline.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/font/DejaVu Sans Mono for Powerline.ttf -------------------------------------------------------------------------------- /mini_apps/font/Ubuntu Mono derivative Powerline.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/font/Ubuntu Mono derivative Powerline.ttf -------------------------------------------------------------------------------- /mini_apps/font/simsun.ttc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/font/simsun.ttc -------------------------------------------------------------------------------- /mini_apps/graph.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/14 下午11:06 4 | # @Author : MiracleYoung 5 | # @File : graph.py 6 | 7 | def search_graph(graph: dict, start, end): 8 | _ret = [] 9 | generate_path(graph, [start], end, _ret) 10 | # 这一步的排序可有可无,只不过为了显示好看 11 | _ret.sort(key=lambda x: len(x)) 12 | return _ret 13 | 14 | 15 | def generate_path(graph: dict, path, end, ret: list): 16 | _state = path[-1] 17 | # 如果起始点和终点是同一个位置,则结束 18 | if _state == end: 19 | ret.append(path) 20 | else: 21 | for _item in graph[_state]: 22 | if _item not in path: 23 | # path + [_item] 就是递归调用的关键参数,path的组成 24 | generate_path(graph, path + [_item], end, ret) 25 | 26 | 27 | if __name__ == '__main__': 28 | _GRAPH = {'A': ['B', 'C', 'D'], 29 | 'B': ['E'], 30 | 'C': ['D', 'F'], 31 | 'D': ['B', 'E', 'G'], 32 | 'E': [], 33 | 'F': ['D', 'G'], 34 | 'G': ['E']} 35 | _ret = search_graph(_GRAPH, 'A', 'E') 36 | print("******************") 37 | print(' path A to E') 38 | print("******************") 39 | for i in _ret: 40 | print(i) 41 | -------------------------------------------------------------------------------- /mini_apps/imdbtop250/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/2/20 6:42 AM 4 | 5 | __author__ = 'Miracle' -------------------------------------------------------------------------------- /mini_apps/imdbtop250/imdbtop250.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/2/20 5:18 AM 4 | 5 | __author__ = 'Miracle' 6 | 7 | 8 | from urllib import request 9 | from chardet import detect 10 | from bs4 import BeautifulSoup 11 | import pandas as pd 12 | import time 13 | import random 14 | 15 | 16 | def getSoup(url): 17 | ''' 18 | 获取网页源码,生成soup对象 19 | ''' 20 | with request.urlopen(url) as fp: 21 | byt = fp.read() 22 | det = detect(byt) 23 | time.sleep(random.randrange(1, 5)) 24 | return BeautifulSoup(byt.decode(det['encoding']), 'lxml') 25 | 26 | 27 | def getData(soup): 28 | ''' 29 | 解析数据 30 | ''' 31 | 32 | # 获取评分 33 | ol = soup.find('tbody', attrs={'class': 'lister-list'}) 34 | score_info = ol.find_all('td', attrs={'class': 'imdbRating'}) 35 | film_scores = [k.text.replace('\n', '') for k in score_info] 36 | 37 | # 获取评分、电影名、导演・演员、上映年份、详情网页链接 38 | film_info = ol.find_all('td', attrs={'class': 'titleColumn'}) 39 | film_names = [k.find('a').text for k in film_info] 40 | film_actors = [k.find('a').attrs['title'] for k in film_info] 41 | film_years = [k.find('span').text[1:5] for k in film_info] 42 | next_nurl = [url2 + k.find('a').attrs['href'][0:17] for k in film_info] 43 | data = pd.DataFrame( 44 | {'name': film_names, 'year': film_years, 'score': film_scores, 'actors': film_actors, 'newurl': next_nurl}) 45 | return data 46 | 47 | 48 | def nextUrl(detail, detail1): 49 | ''' 50 | 获取详情页数据 51 | ''' 52 | 53 | # 获取电影国家 54 | detail_list = detail.find('div', attrs={'id': 'titleDetails'}).find_all('div', attrs={'class': 'txt-block'}) 55 | detail_str = [k.text.replace('\n', '') for k in detail_list] 56 | detail_str = [k for k in detail_str if k.find(':') >= 0] 57 | detail_dict = {k.split(':')[0]: k.split(':')[1] for k in detail_str} 58 | country = detail_dict['Country'] 59 | 60 | # 获取电影类型 61 | detail_list1 = detail.find('div', attrs={'class': 'title_wrapper'}).find_all('div', attrs={'class': 'subtext'}) 62 | detail_str1 = [k.find('a').text for k in detail_list1] 63 | movie_type = pd.DataFrame({'Type': detail_str1}) 64 | 65 | # 获取以组划分的电影详细评分、人数 66 | div_list = detail1.find_all('td', attrs={'align': 'center'}) 67 | value = [k.find('div', attrs={'class': 'bigcell'}).text.strip() for k in div_list] 68 | num = [k.find('div', attrs={'class': 'smallcell'}).text.strip() for k in div_list] 69 | scores = pd.DataFrame({'value': value, 'num': num}) 70 | return country, movie_type, scores 71 | 72 | 73 | if __name__ == '__main__': 74 | url = "https://www.imdb.com/chart/top" 75 | url2 = "https://www.imdb.com" 76 | soup = getSoup(url) 77 | print(getData(soup)) 78 | movie_data = getData(soup) 79 | movie_data['country'] = 'Unknown' 80 | movie_data['Type'] = 'Unknown' 81 | movie_data['scores'] = 'Unknown' 82 | movie_data['nums'] = 'Unknown' 83 | b = movie_data['newurl'] 84 | this_type = movie_data['Type'] 85 | for i in range(len(b)): 86 | soup3 = getSoup(b[i]) 87 | soup4 = getSoup(b[i] + 'ratings') 88 | this_country, this_type, this_score = nextUrl(soup3, soup4) 89 | movie_data['country'][i] = this_country 90 | movie_data['Type'][i] = list(this_type['Type']) 91 | movie_data['scores'][i] = list(this_score['value']) 92 | movie_data['nums'][i] = list(this_score['num']) 93 | print(i) 94 | -------------------------------------------------------------------------------- /mini_apps/img/img.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/img/img.jpeg -------------------------------------------------------------------------------- /mini_apps/img/jgz.jpeg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/img/jgz.jpeg -------------------------------------------------------------------------------- /mini_apps/jgz.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/1/25 2:00 PM 4 | 5 | __author__ = 'Miracle' 6 | 7 | from PIL import Image, ImageDraw, ImageFont 8 | 9 | img = Image.open("./img/img.jpeg") 10 | jgz = Image.open("./img/jgz.jpeg") 11 | img.paste(jgz, (63, 46)) 12 | 13 | # 控制表情的叠加位置 14 | draw = ImageDraw.Draw(img) 15 | # 字体自己随便找一个 16 | font = ImageFont.truetype('./font/simsun.ttc', 24) 17 | draw.text((16, 200), "Python专栏", fill=(0, 0, 0), font=font) 18 | 19 | # 控制文字添加位置 20 | img.show() 21 | img.save("生成的表情包.jpg") 22 | -------------------------------------------------------------------------------- /mini_apps/lambda_ex.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/14 下午10:18 4 | # @Author : MiracleYoung 5 | # @File : lambda_ex.py 6 | 7 | _ = ( 8 | 255, 9 | lambda 10 | V ,B,c 11 | :c and Y(V*V+B,B, c 12 | -1)if(abs(V)<6)else 13 | ( 2+c-4*abs(V)**-0.4)/i 14 | ) ;v, x=1500,1000;C=range(v*x 15 | );import struct;P=struct.pack;M,\ 16 | j ='0 else' ')for x in range(-30,30)])for y in range(15,-15,-1)])) -------------------------------------------------------------------------------- /mini_apps/lover7c.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/8/13 下午10:20 4 | # @Author : MiracleYoung 5 | # @File : lover7c.py 6 | 7 | import seaborn as sns 8 | import numpy as np 9 | from pylab import * 10 | import matplotlib.pyplot as plt 11 | 12 | # Define Data 13 | data = np.zeros([62, 65], dtype="float") 14 | 15 | # Begin to Draw 16 | POS_VALUE = 1 17 | NEG_VALUE = -1 18 | 19 | # 绘制第一个 "M" 20 | data[1:31, 1] = POS_VALUE 21 | 22 | for i in range(1, 11): 23 | data[i, i] = POS_VALUE 24 | for i in range(11, 21): 25 | data[21 - i, i] = POS_VALUE 26 | 27 | data[1:31, 20] = POS_VALUE 28 | data[2, 31:34] = POS_VALUE 29 | 30 | # 绘制 "O" 31 | for i in range(0, 7): 32 | data[i + 2, 31 - i] = POS_VALUE 33 | 34 | data[8:25, 25] = POS_VALUE 35 | for i in range(25, 32): 36 | data[i, i] = POS_VALUE 37 | 38 | data[31, 31:34] = POS_VALUE 39 | for i in range(34, 41): 40 | data[65 - i, i] = POS_VALUE 41 | 42 | data[8:25, 40] = POS_VALUE 43 | for i in range(0, 7): 44 | data[i + 2, i + 34] = POS_VALUE 45 | 46 | # 绘制第二个 “M” 47 | data[1:31, 44] = POS_VALUE 48 | for i in range(1, 11): 49 | data[i, 43 + i] = POS_VALUE 50 | for i in range(11, 21): 51 | data[21 - i, 43 + i] = POS_VALUE 52 | data[1:31, 63] = POS_VALUE 53 | 54 | # 绘制 “心” 55 | for i in range(37, 44): 56 | data[i, i - 11] = NEG_VALUE 57 | for i in range(37, 44): 58 | data[i, 64 - i] = NEG_VALUE 59 | for i in range(44, 57): 60 | data[i, i - 23] = NEG_VALUE 61 | data[i, i - 22] = NEG_VALUE 62 | data[i - 1, i - 22] = NEG_VALUE 63 | data[i - 1, i - 21] = NEG_VALUE 64 | data[i - 2, i - 21] = NEG_VALUE 65 | data[i - 2, i - 20] = NEG_VALUE 66 | data[i - 3, i - 20] = NEG_VALUE 67 | data[i - 3, i - 19] = NEG_VALUE 68 | data[i - 4, i - 19] = NEG_VALUE 69 | data[i - 4, i - 18] = NEG_VALUE 70 | data[i - 5, i - 18] = NEG_VALUE 71 | data[i - 5, i - 17] = NEG_VALUE 72 | 73 | for i in range(44, 57): 74 | data[i, 89 - i] = NEG_VALUE 75 | data[i, 88 - i] = NEG_VALUE 76 | data[i - 1, 88 - i] = NEG_VALUE 77 | data[i - 1, 87 - i] = NEG_VALUE 78 | data[i - 2, 87 - i] = NEG_VALUE 79 | data[i - 2, 86 - i] = NEG_VALUE 80 | data[i - 3, 86 - i] = NEG_VALUE 81 | data[i - 3, 85 - i] = NEG_VALUE 82 | data[i - 4, 85 - i] = NEG_VALUE 83 | data[i - 4, 84 - i] = NEG_VALUE 84 | data[i - 5, 84 - i] = NEG_VALUE 85 | data[i - 5, 83 - i] = NEG_VALUE 86 | data[i - 6, 83 - i] = NEG_VALUE 87 | 88 | for i in range(37, 44): 89 | data[i, i + 2] = NEG_VALUE 90 | for i in range(37, 45): 91 | data[i, 77 - i] = NEG_VALUE 92 | 93 | # 绘制 “I” 94 | data[33:59, 11] = NEG_VALUE 95 | data[33, 9:14] = NEG_VALUE 96 | data[59, 9:14] = NEG_VALUE 97 | 98 | # 绘制 “U” 99 | data[33:53, 47] = NEG_VALUE 100 | for i in range(53, 60): 101 | data[i, i - 6] = NEG_VALUE 102 | 103 | data[59, 53:56] = NEG_VALUE 104 | 105 | for i in range(0, 6): 106 | data[59 - i, i + 55] = NEG_VALUE 107 | 108 | data[33:54, 61] = NEG_VALUE 109 | 110 | # SHOW THE MAP 111 | plt.figure(figsize=(15, 10)) 112 | sns.heatmap(-data, xticklabels=False, yticklabels=False) 113 | show() -------------------------------------------------------------------------------- /mini_apps/maze.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/13 下午10:25 4 | # @Author : MiracleYoung 5 | # @File : draw_heart.py 6 | 7 | print(''.join(__import__('random').choice('\u2571\u2572') for i in range(50*24))) -------------------------------------------------------------------------------- /mini_apps/mouse_keyboard_controller.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/7/12 上午6:53 4 | # @Author : MiracleYoung 5 | # @File : mouse_keyboard_controller.py 6 | 7 | # from pynput import mouse, keyboard 8 | 9 | # from pynput.mouse import Controller, Button 10 | # 11 | # mouse = Controller() 12 | # 13 | # # 获取当前鼠标位置 14 | # print(f'当前小胖的鼠标位置是: {mouse.position}') 15 | # 16 | # # 设置鼠标位置 17 | # mouse.position = (10, 20) 18 | # print(f'现在小胖把鼠标移动到 {mouse.position}') 19 | # 20 | # # 使用相对距离,移动当前鼠标 21 | # mouse.move(5, -5) 22 | # 23 | # # 按下鼠标左键,释放鼠标左键 24 | # mouse.press(Button.left) 25 | # mouse.release(Button.left) 26 | # 27 | # # 向下滚动2格 28 | # mouse.scroll(0, 2) 29 | 30 | # from pynput import mouse 31 | # 32 | # def on_move(x, y): 33 | # print(f'鼠标移动到坐标 {(x, y)}') 34 | # 35 | # def on_click(x, y, button, pressed): 36 | # print(f"{'按下' if pressed else '释放'} ,当前位置是: {(x, y)}") 37 | # if not pressed: 38 | # # 停止监听 39 | # return False 40 | # 41 | # def on_scroll(x, y, dx, dy): 42 | # print(f"滑动鼠标, {'向下' if dy < 0 else '向上'} at {(x, y)}") 43 | # 44 | # # 一直监听事件,直到鼠标释放 45 | # with mouse.Listener( 46 | # on_move=on_move, 47 | # on_click=on_click, 48 | # on_scroll=on_scroll) as listener: 49 | # listener.join() 50 | 51 | 52 | # from pynput.keyboard import Key, Controller 53 | # 54 | # keyboard = Controller() 55 | # 56 | # # 按下并释放空格 57 | # keyboard.press(Key.space) 58 | # keyboard.release(Key.space) 59 | # 60 | # # 按下并释放小写字母a 61 | # keyboard.press('a') 62 | # keyboard.release('a') 63 | # 64 | # # 2种方式输入大写A 65 | # keyboard.press('A') 66 | # keyboard.release('A') 67 | # with keyboard.pressed(Key.shift): 68 | # keyboard.press('a') 69 | # keyboard.release('a') 70 | # 71 | # # 直接操作键盘输入Hello World 72 | # keyboard.type('Hello World') 73 | 74 | 75 | from pynput import keyboard 76 | 77 | def on_press(key): 78 | try: 79 | print(f'字母 {key.char} 被按下了') 80 | except AttributeError: 81 | print(f'特殊的键 {key} 被按下了') 82 | 83 | def on_release(key): 84 | print(f'{key} 被释放了') 85 | if key == keyboard.Key.esc: 86 | # 停止监听 87 | return False 88 | 89 | # 一直监听键盘事件,直到停止 90 | with keyboard.Listener( 91 | on_press=on_press, 92 | on_release=on_release) as listener: 93 | listener.join() -------------------------------------------------------------------------------- /mini_apps/progressbar/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/1 下午9:00 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /mini_apps/progressbar/stdout.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/1 下午9:00 4 | # @Author : MiracleYoung 5 | # @File : app.py 6 | 7 | import sys 8 | import time 9 | 10 | def progress_bar(total): 11 | """ 12 | 进度条效果 13 | """ 14 | # 获取标准输出 15 | _output = sys.stdout 16 | # 通过参数决定你的进度条总量是多少 17 | for count in range(0, total + 1): 18 | # 这里的second只是作为工作量的一种代替 19 | # 这里应该是有你的主程序,main() 20 | _second = 0.1 21 | # 模拟业务的消耗时间 22 | time.sleep(_second) 23 | # 输出进度条 24 | _output.write(f'\rcomplete percent:{count:.0f}') 25 | # 将标准输出一次性刷新 26 | _output.flush() 27 | 28 | progress_bar(100) -------------------------------------------------------------------------------- /mini_apps/progressbar/use_tqdm.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/8 上午6:07 4 | # @Author : MiracleYoung 5 | # @File : tqdm.py 6 | 7 | from time import sleep 8 | from tqdm import trange, tqdm 9 | from multiprocessing import Pool, freeze_support, RLock 10 | 11 | L = list(range(9)) 12 | 13 | def progresser(n): 14 | interval = 0.001 / (n + 2) 15 | total = 5000 16 | text = "#{}, est. {:<04.2}s".format(n, interval * total) 17 | for i in trange(total, desc=text, position=n): 18 | sleep(interval) 19 | 20 | if __name__ == '__main__': 21 | freeze_support() # for Windows support 22 | p = Pool(len(L), 23 | # again, for Windows support 24 | initializer=tqdm.set_lock, initargs=(RLock(),)) 25 | p.map(progresser, L) 26 | print("\n" * (len(L) - 2)) -------------------------------------------------------------------------------- /mini_apps/tar2zip/1-2.tar.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/tar2zip/1-2.tar.gz -------------------------------------------------------------------------------- /mini_apps/tar2zip/1-2.zip: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/tar2zip/1-2.zip -------------------------------------------------------------------------------- /mini_apps/tar2zip/1.txt: -------------------------------------------------------------------------------- 1 | tarfile -------------------------------------------------------------------------------- /mini_apps/tar2zip/2.txt: -------------------------------------------------------------------------------- 1 | tarfile -------------------------------------------------------------------------------- /mini_apps/tar2zip/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/5/31 下午10:15 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /mini_apps/tar2zip/helper.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/5/31 下午10:15 4 | # @Author : MiracleYoung 5 | # @File : helper.py 6 | 7 | -------------------------------------------------------------------------------- /mini_apps/tar2zip/tar2zip.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/5/31 下午10:15 4 | # @Author : MiracleYoung 5 | # @File : tar2zip.py 6 | 7 | 8 | import tarfile, zipfile, glob, os, time 9 | from io import BytesIO 10 | 11 | 12 | def getuser(): 13 | # 模拟返回用户名、用户id 14 | return "Miracle", 666 15 | 16 | 17 | def getmode(name, data): 18 | # 返回文件类型,"b" 或 "t" 19 | # 假设我们现在都是字符 20 | return "t" 21 | 22 | 23 | now = time.time() 24 | user = getuser() 25 | 26 | 27 | def fixup(infile): 28 | file, ext = os.path.splitext(infile) 29 | outfile = file + ".tar.gz" 30 | print(f'outfile: {outfile}') 31 | 32 | zip = zipfile.ZipFile(infile, "r") 33 | tar = tarfile.open(outfile, "w:gz") # 使用gzip、写 模式打开 34 | tar.posix = 1 35 | 36 | for name in zip.namelist(): 37 | if name.endswith("/"): 38 | continue 39 | 40 | data = zip.read(name) 41 | if getmode(name, data) == "t": 42 | data = data.decode().replace("\r\n", "\n") 43 | 44 | tarinfo = tarfile.TarInfo() 45 | tarinfo.name = name 46 | tarinfo.size = len(data) 47 | tarinfo.mtime = now 48 | tarinfo.uname = tarinfo.gname = user[0] 49 | tarinfo.uid = tarinfo.gid = user[1] 50 | tar.addfile(tarinfo, BytesIO(data.encode())) 51 | 52 | tar.close() 53 | zip.close() 54 | 55 | 56 | if __name__ == '__main__': 57 | # convert all ZIP files in the current directory 58 | for file in glob.glob("*.zip"): 59 | fixup(file) 60 | -------------------------------------------------------------------------------- /mini_apps/tar2zip/tmp.txt: -------------------------------------------------------------------------------- 1 | fsadfsdf 2 | fsadfsdf 3 | fsadfsdf 4 | fsadfsdf 5 | fsadfsdffsadfsdf 6 | 7 | 8 | 9 | -------------------------------------------------------------------------------- /mini_apps/test_func.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/8/21 下午9:56 4 | # @Author : MiracleYoung 5 | # @File : test_func.py 6 | 7 | # def testFun(): 8 | # temp = [lambda x: i * x for i in range(4)] 9 | # return temp 10 | # 11 | # 12 | # for everyLambda in testFun(): 13 | # print(everyLambda(2)) 14 | 15 | 16 | # def testFun(): 17 | # temp = [lambda x, i=i: i * x for i in range(4)] 18 | # return temp 19 | # 20 | # 21 | # for everyLambda in testFun(): 22 | # print(everyLambda(2)) 23 | 24 | # from functools import partial 25 | # from operator import mul 26 | # 27 | # 28 | # def testFun(): 29 | # return [partial(mul, i) for i in range(4)] 30 | # 31 | # 32 | # for everyLambda in testFun(): 33 | # print(everyLambda(2)) 34 | # 35 | # 36 | # def testFun(): 37 | # return (lambda x, i=i: i * x for i in range(4)) 38 | # 39 | # 40 | # for everyLambda in testFun(): 41 | # print(everyLambda(2)) 42 | # 43 | # 44 | def testFun(): 45 | for i in range(4): 46 | yield lambda x: i * x 47 | 48 | 49 | for everyLambda in testFun(): 50 | print(everyLambda(2)) 51 | -------------------------------------------------------------------------------- /mini_apps/weibo_login.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/12/24 6:19 AM 4 | 5 | __author__ = 'Miracle' 6 | 7 | import urllib.request 8 | import urllib.parse 9 | from http import cookiejar 10 | import requests 11 | import base64 12 | import re 13 | import json 14 | import hashlib 15 | 16 | # 处理cookie,让cookie以后一直跟着走 17 | cj = cookiejar.CookieJar() 18 | cookie_support = urllib.request.HTTPCookieProcessor(cj) 19 | opener = urllib.request.build_opener(cookie_support, urllib.request.HTTPHandler) 20 | urllib.request.install_opener(opener) 21 | 22 | postdata = { 23 | 'entry': 'weibo', 24 | 'gateway': '1', 25 | 'from': '', 26 | 'savestate': '7', 27 | 'userticket': '1', 28 | 'ssosimplelogin': '1', 29 | 'vsnf': '1', 30 | 'vsnval': '', 31 | 'su': '', 32 | 'service': 'miniblog', 33 | 'servertime': '', 34 | 'nonce': '', 35 | 'pwencode': 'wsse', 36 | 'sp': '', 37 | 'encoding': 'UTF-8', 38 | 'url': 'http://weibo.com/ajaxlogin.php?framelogin=1&callback=parent.sinaSSOController.feedBackUrlCallBack', 39 | 'returntype': 'META' 40 | } 41 | 42 | 43 | def get_servertime(): 44 | url = 'http://login.sina.com.cn/sso/prelogin.php?entry=weibo&callback=sinaSSOController.preloginCallBack&su=dW5kZWZpbmVk&client=ssologin.js(v1.3.18)&_=1329806375939' 45 | # 返回出来的是一个Response对象,无法直接获取,text后,可以通过正则匹配到 46 | # 大概长这样子的:sinaSSOController.preloginCallBack({"retcode":0,"servertime":1545606770, ...}) 47 | data = requests.request('GET', url).text 48 | p = re.compile('\((.*)\)') 49 | try: 50 | json_data = p.search(data).group(1) 51 | data = json.loads(json_data) 52 | servertime = str(data['servertime']) 53 | nonce = data['nonce'] 54 | return servertime, nonce 55 | except: 56 | print('获取 severtime 失败!') 57 | return None 58 | 59 | 60 | def get_pwd(pwd, servertime, nonce): 61 | # 第一次计算,注意Python3 的加密需要encode,使用bytes 62 | pwd1 = hashlib.sha1(pwd.encode()).hexdigest() 63 | # 使用pwd1的结果在计算第二次 64 | pwd2 = hashlib.sha1(pwd1.encode()).hexdigest() 65 | # 使用第二次的结果再加上之前计算好的servertime和nonce值,hash一次 66 | pwd3_ = pwd2 + servertime + nonce 67 | pwd3 = hashlib.sha1(pwd3_.encode()).hexdigest() 68 | return pwd3 69 | 70 | 71 | def get_user(username): 72 | # 将@符号转换成url中能够识别的字符 73 | _username = urllib.request.quote(username) 74 | # Python3中的base64计算也是要字节 75 | # base64出来后,最后有一个换行符,所以用了切片去了最后一个字符 76 | username = base64.encodebytes(_username.encode())[:-1] 77 | return username 78 | 79 | 80 | def login(): 81 | username = 'yangqinglin_19900723@hotmail.com' 82 | pwd = ',yql0723,' 83 | url = 'http://login.sina.com.cn/sso/login.php?client=ssologin.js(v1.3.18)' 84 | try: 85 | servertime, nonce = get_servertime() 86 | except: 87 | return 88 | global postdata 89 | postdata['servertime'] = servertime 90 | postdata['nonce'] = nonce 91 | postdata['su'] = get_user(username) 92 | postdata['sp'] = get_pwd(pwd, servertime, nonce) 93 | 94 | postdata = urllib.parse.urlencode(postdata) 95 | headers = { 96 | 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_1) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/71.0.3578.98 Safari/537.36' 97 | } 98 | req = requests.request( 99 | method='POST', 100 | url=url, 101 | data=postdata, 102 | headers=headers 103 | ) 104 | ret = req.text 105 | p = re.compile('location\.replace\(\"(.*?)\"\)') 106 | try: 107 | login_url = p.search(ret).group(1) 108 | requests.request('GET', login_url) 109 | print("登录成功!") 110 | except: 111 | print('登陆失败!') 112 | 113 | login() 114 | -------------------------------------------------------------------------------- /mini_apps/xzpq.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2019/1/4 6:56 AM 4 | 5 | __author__ = 'Miracle' 6 | 7 | ''' 8 | 小猪佩奇 9 | ''' 10 | 11 | import turtle as t 12 | 13 | 14 | def init_pen(): 15 | ''' 16 | 初始化画笔的一些属性 17 | ''' 18 | t.pensize(4) # 设置画笔的大小 19 | t.colormode(255) # 设置GBK颜色范围为0-255 20 | t.color((255, 155, 192), "pink") # 设置画笔颜色和填充颜色(pink) 21 | t.setup(900, 500) # 设置主窗口的大小为900*500 22 | t.speed(10) # 设置画笔速度为10 23 | 24 | 25 | def norse(): 26 | ''' 27 | 鼻子 28 | ''' 29 | t.pu() # 提笔 30 | t.goto(-100, 100) # 画笔前往坐标(-100,100) 31 | t.pd() # 下笔 32 | t.seth(-30) # 笔的角度为-30° 33 | t.begin_fill() # 外形填充的开始标志 34 | a = 0.4 35 | for i in range(120): 36 | if 0 <= i < 30 or 60 <= i < 90: 37 | a = a + 0.08 38 | t.lt(3) # 向左转3度 39 | t.fd(a) # 向前走a的步长 40 | else: 41 | a = a - 0.08 42 | t.lt(3) 43 | t.fd(a) 44 | t.end_fill() # 依据轮廓填充 45 | t.pu() # 提笔 46 | t.seth(90) # 笔的角度为90度 47 | t.fd(25) # 向前移动25 48 | t.seth(0) # 转换画笔的角度为0 49 | t.fd(10) 50 | t.pd() 51 | t.pencolor(255, 155, 192) # 设置画笔颜色 52 | t.seth(10) 53 | t.begin_fill() 54 | t.circle(5) # 画一个半径为5的圆 55 | t.color(160, 82, 45) # 设置画笔和填充颜色 56 | t.end_fill() 57 | t.pu() 58 | t.seth(0) 59 | t.fd(20) 60 | t.pd() 61 | t.pencolor(255, 155, 192) 62 | t.seth(10) 63 | t.begin_fill() 64 | t.circle(5) 65 | t.color(160, 82, 45) 66 | t.end_fill() 67 | 68 | 69 | def head(): 70 | ''' 71 | 头 72 | ''' 73 | t.color((255, 155, 192), "pink") 74 | t.pu() 75 | t.seth(90) 76 | t.fd(41) 77 | t.seth(0) 78 | t.fd(0) 79 | t.pd() 80 | t.begin_fill() 81 | t.seth(180) 82 | t.circle(300, -30) # 顺时针画一个半径为300,圆心角为30°的园 83 | t.circle(100, -60) 84 | t.circle(80, -100) 85 | t.circle(150, -20) 86 | t.circle(60, -95) 87 | t.seth(161) 88 | t.circle(-300, 15) 89 | t.pu() 90 | t.goto(-100, 100) 91 | t.pd() 92 | t.seth(-30) 93 | a = 0.4 94 | for i in range(60): 95 | if 0 <= i < 30 or 60 <= i < 90: 96 | a = a + 0.08 97 | t.lt(3) # 向左转3度 98 | t.fd(a) # 向前走a的步长 99 | else: 100 | a = a - 0.08 101 | t.lt(3) 102 | t.fd(a) 103 | t.end_fill() 104 | 105 | 106 | def ear(): 107 | ''' 108 | 耳朵 109 | ''' 110 | t.color((255, 155, 192), "pink") 111 | t.pu() 112 | t.seth(90) 113 | t.fd(-7) 114 | t.seth(0) 115 | t.fd(70) 116 | t.pd() 117 | t.begin_fill() 118 | t.seth(100) 119 | t.circle(-50, 50) 120 | t.circle(-10, 120) 121 | t.circle(-50, 54) 122 | t.end_fill() 123 | t.pu() 124 | t.seth(90) 125 | t.fd(-12) 126 | t.seth(0) 127 | t.fd(30) 128 | t.pd() 129 | t.begin_fill() 130 | t.seth(100) 131 | t.circle(-50, 50) 132 | t.circle(-10, 120) 133 | t.circle(-50, 56) 134 | t.end_fill() 135 | 136 | 137 | def eye(): 138 | ''' 139 | 眼睛 140 | ''' 141 | t.color((255, 155, 192), "white") 142 | t.pu() 143 | t.seth(90) 144 | t.fd(-20) 145 | t.seth(0) 146 | t.fd(-95) 147 | t.pd() 148 | t.begin_fill() 149 | t.circle(15) 150 | t.end_fill() 151 | t.color("black") 152 | t.pu() 153 | t.seth(90) 154 | t.fd(12) 155 | t.seth(0) 156 | t.fd(-3) 157 | t.pd() 158 | t.begin_fill() 159 | t.circle(3) 160 | t.end_fill() 161 | t.color((255, 155, 192), "white") 162 | t.pu() 163 | t.seth(90) 164 | t.fd(-25) 165 | t.seth(0) 166 | t.fd(40) 167 | t.pd() 168 | t.begin_fill() 169 | t.circle(15) 170 | t.end_fill() 171 | t.color("black") 172 | t.pu() 173 | t.seth(90) 174 | t.fd(12) 175 | t.seth(0) 176 | t.fd(-3) 177 | t.pd() 178 | t.begin_fill() 179 | t.circle(3) 180 | t.end_fill() 181 | 182 | 183 | def blusher(): 184 | ''' 185 | 腮 186 | ''' 187 | t.color((255, 155, 192)) 188 | t.pu() 189 | t.seth(90) 190 | t.fd(-95) 191 | t.seth(0) 192 | t.fd(65) 193 | t.pd() 194 | t.begin_fill() 195 | t.circle(30) 196 | t.end_fill() 197 | 198 | 199 | def mouth(): 200 | ''' 201 | 嘴 202 | ''' 203 | t.color(239, 69, 19) 204 | t.pu() 205 | t.seth(90) 206 | t.fd(15) 207 | t.seth(0) 208 | t.fd(-100) 209 | t.pd() 210 | t.seth(-80) 211 | t.circle(30, 40) 212 | t.circle(40, 80) 213 | 214 | 215 | def body(): 216 | ''' 217 | 身体 218 | ''' 219 | t.color("red", (255, 99, 71)) 220 | t.pu() 221 | t.seth(90) 222 | t.fd(-20) 223 | t.seth(0) 224 | t.fd(-78) 225 | t.pd() 226 | t.begin_fill() 227 | t.seth(-130) 228 | t.circle(100, 10) 229 | t.circle(300, 30) 230 | t.seth(0) 231 | t.fd(230) 232 | t.seth(90) 233 | t.circle(300, 30) 234 | t.circle(100, 3) 235 | t.color((255, 155, 192), (255, 100, 100)) 236 | t.seth(-135) 237 | t.circle(-80, 63) 238 | t.circle(-150, 24) 239 | t.end_fill() 240 | 241 | 242 | def hand(): 243 | ''' 244 | 手 245 | ''' 246 | t.color((255, 155, 192)) 247 | t.pu() 248 | t.seth(90) 249 | t.fd(-40) 250 | t.seth(0) 251 | t.fd(-27) 252 | t.pd() 253 | t.seth(-160) 254 | t.circle(300, 15) 255 | t.pu() 256 | t.seth(90) 257 | t.fd(15) 258 | t.seth(0) 259 | t.fd(0) 260 | t.pd() 261 | t.seth(-10) 262 | t.circle(-20, 90) 263 | t.pu() 264 | t.seth(90) 265 | t.fd(30) 266 | t.seth(0) 267 | t.fd(237) 268 | t.pd() 269 | t.seth(-20) 270 | t.circle(-300, 15) 271 | t.pu() 272 | t.seth(90) 273 | t.fd(20) 274 | t.seth(0) 275 | t.fd(0) 276 | t.pd() 277 | t.seth(-170) 278 | t.circle(20, 90) 279 | 280 | 281 | def foot(): 282 | ''' 283 | 脚 284 | ''' 285 | t.pensize(10) 286 | t.color((240, 128, 128)) 287 | t.pu() 288 | t.seth(90) 289 | t.fd(-75) 290 | t.seth(0) 291 | t.fd(-180) 292 | t.pd() 293 | t.seth(-90) 294 | t.fd(40) 295 | t.seth(-180) 296 | t.color("black") 297 | t.pensize(15) 298 | t.fd(20) 299 | t.pensize(10) 300 | t.color((240, 128, 128)) 301 | t.pu() 302 | t.seth(90) 303 | t.fd(40) 304 | t.seth(0) 305 | t.fd(90) 306 | t.pd() 307 | t.seth(-90) 308 | t.fd(40) 309 | t.seth(-180) 310 | t.color("black") 311 | t.pensize(15) 312 | t.fd(20) 313 | 314 | 315 | def tail(): 316 | ''' 317 | 尾巴 318 | ''' 319 | t.pensize(4) 320 | t.color((255, 155, 192)) 321 | t.pu() 322 | t.seth(90) 323 | t.fd(70) 324 | t.seth(0) 325 | t.fd(95) 326 | t.pd() 327 | t.seth(0) 328 | t.circle(70, 20) 329 | t.circle(10, 330) 330 | t.circle(70, 30) 331 | 332 | 333 | def main(): 334 | init_pen() 335 | norse() 336 | head() 337 | ear() 338 | eye() 339 | blusher() 340 | mouth() 341 | body() 342 | hand() 343 | foot() 344 | tail() 345 | 346 | 347 | if __name__ == '__main__': 348 | main() 349 | # 能够停住画布,不至于迅速结束 350 | t.mainloop() 351 | -------------------------------------------------------------------------------- /mini_apps/生成的表情包.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/MiracleYoung/exercises/e42c0df4bcabef2844a9583d2ed08c3a365a979b/mini_apps/生成的表情包.jpg -------------------------------------------------------------------------------- /python_data_structure/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/13/18 4:23 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/algorithm/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/13/18 3:06 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/algorithm/dct.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/13/18 4:22 PM 4 | # @Author : Miracle Young 5 | # @File : dct.py 6 | 7 | import timeit 8 | import random 9 | 10 | for i in range(10000, 10000001, 20000): 11 | ret = timeit.Timer("random.randrange(%d) in x" % i, "from __main__ import random, x") 12 | x = list(range(i)) 13 | lst_time = ret.timeit(number=1000) 14 | x = {j: None for j in range(i)} 15 | d_time = ret.timeit(number=1000) 16 | print("%d, %10.3f, %10.3f" % (i, lst_time, d_time)) -------------------------------------------------------------------------------- /python_data_structure/algorithm/disorder.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/13/18 3:07 PM 4 | # @Author : Miracle Young 5 | # @File : disorder.py 6 | 7 | def disorder_iter(s1, s2): 8 | _pos1 = 0 9 | _lst2 = list(s2) 10 | _ok = True 11 | while _pos1 < len(s1) and _ok: 12 | _pos2 = 0 13 | _found = False 14 | while _pos2 < len(_lst2) and not _found: 15 | if s1[_pos1] == _lst2[_pos2]: 16 | _lst2[_pos2] = None 17 | _found = True 18 | else: 19 | _pos2 += 1 20 | 21 | # if exist one letter does not exist in s2, exit 22 | if not _found: 23 | _ok = False 24 | 25 | _pos1 += 1 26 | return _ok 27 | 28 | 29 | def disorder_sort(s1, s2): 30 | _l1, _l2 = list(s1), list(s2) 31 | _ok = True 32 | _pos = 0 33 | _l1.sort() 34 | _l2.sort() 35 | while _pos < len(_l1) and _ok: 36 | if _l1[_pos] == _l2[_pos]: 37 | _pos += 1 38 | else: 39 | _ok = False 40 | return _ok 41 | 42 | 43 | def disorder_dict(s1, s2): 44 | _d1, _d2 = [0] * 26, [0] * 26 45 | for _, _letter in enumerate(s1): 46 | _d1[ord(_letter) - ord('a')] += 1 47 | 48 | for _, _letter in enumerate(s2): 49 | _d2[ord(_letter) - ord('a')] += 1 50 | 51 | 52 | _d3, _d4 = {}, {} 53 | for _, _letter in enumerate(s1): 54 | _d3[_letter] 55 | _ok = True 56 | 57 | for i in range(26): 58 | if _d1[i] == _d2[i]: 59 | continue 60 | else: 61 | _ok = False 62 | 63 | return _ok 64 | 65 | 66 | 67 | if __name__ == '__main__': 68 | import timeit 69 | ret = timeit.Timer('disorder_iter("abc", "cba")', "from __main__ import disorder_iter") 70 | print(ret.timeit(number=10000000)) 71 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 11:13 AM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/advance_check_brackets.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 1:44 PM 4 | # @Author : Miracle Young 5 | # @File : advance_check_brackets.py 6 | 7 | from python_data_structure.base_data_structure.stack import Stack 8 | 9 | 10 | def check_brackets(s): 11 | _stack = Stack() 12 | _ok = True 13 | _index = 0 14 | while _index < len(s) and _ok: 15 | if s[_index] in '([{': 16 | _stack.push(s[_index]) 17 | else: 18 | if _stack.is_empty(): 19 | _ok = False 20 | return _ok 21 | else: 22 | _open = _stack.pop() 23 | # s[_index] is close symbol 24 | if not matches(_open, s[_index]): 25 | _ok = False 26 | return _ok 27 | _index += 1 28 | return _ok and _stack.is_empty() 29 | 30 | 31 | def matches(open, close): 32 | _opens, _closes = '([{', ')]}' 33 | return _opens.index(open) == _closes.index(close) 34 | 35 | 36 | if __name__ == '__main__': 37 | print(check_brackets('({[(){[]}]})')) 38 | print(check_brackets('({[(){]}]})')) 39 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 11:17 AM 4 | # @Author : Miracle Young 5 | # @File : app.py 6 | 7 | 8 | from python_data_structure.base_data_structure.stack import Stack 9 | 10 | _stack = Stack() 11 | 12 | print(_stack.is_empty()) 13 | _stack.push(4) 14 | _stack.push('dog') 15 | print(_stack.peek()) 16 | _stack.push(True) 17 | print(_stack.size()) 18 | print(_stack.is_empty()) 19 | _stack.push(8.4) 20 | print(_stack.pop()) 21 | print(_stack.pop()) 22 | print(_stack.size()) 23 | 24 | 25 | from python_data_structure.base_data_structure.queue import Queue 26 | 27 | _q = Queue() 28 | print(_q.is_empty()) 29 | print(_q.enqueue(1)) 30 | print(_q.enqueue(10)) 31 | print(_q.dequeue()) 32 | print(_q.size()) -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/check_brackets.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 11:38 AM 4 | # @Author : Miracle Young 5 | # @File : check_brackets.py 6 | 7 | 8 | from python_data_structure.base_data_structure.stack import Stack 9 | 10 | def check_par_brackets(s): 11 | _stack = Stack() 12 | _ok = True 13 | _index = 0 14 | while _index < len(s) and _ok: 15 | _item = s[_index] 16 | if _item == '(': 17 | _stack.push(_item) 18 | else: 19 | if _stack.is_empty(): 20 | _ok = False 21 | return _ok 22 | else: 23 | _stack.pop() 24 | _index += 1 25 | # _stack must be empty 26 | return _ok and _stack.is_empty() 27 | 28 | 29 | if __name__ == '__main__': 30 | print(check_par_brackets('((())(())')) 31 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/deque.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/15/18 1:42 PM 4 | # @Author : Miracle Young 5 | # @File : deque.py 6 | 7 | class Deque: 8 | def __init__(self): 9 | self._items = [] 10 | 11 | def add_front(self, item): 12 | self._items.append(item) 13 | 14 | def add_rear(self, item): 15 | self._items.insert(0, item) 16 | 17 | def remove_front(self): 18 | return self._items.pop() 19 | 20 | def remove_rear(self): 21 | return self._items.pop(0) 22 | 23 | def is_empty(self): 24 | return self._items == [] 25 | 26 | def size(self): 27 | return len(self._items) 28 | 29 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/devide_by2.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 2:25 PM 4 | # @Author : Miracle Young 5 | # @File : devide_by2.py 6 | 7 | 8 | from python_data_structure.base_data_structure.stack import Stack 9 | 10 | 11 | def devide_by2(decimal): 12 | _remstack = Stack() 13 | while decimal > 0: 14 | _rem = decimal % 2 15 | _remstack.push(_rem) 16 | decimal //= 2 17 | 18 | _ret = '' 19 | while not _remstack.is_empty(): 20 | _ret += str(_remstack.pop()) 21 | 22 | return _ret 23 | 24 | 25 | def devide_by_base(decimal, base): 26 | _digits = '0123456789ABCDEF' 27 | _remstack = Stack() 28 | while decimal > 0: 29 | _rem = decimal % base 30 | _remstack.push(_rem) 31 | decimal //= base 32 | 33 | _ret = '' 34 | while not _remstack.is_empty(): 35 | _ret += str(_digits[_remstack.pop()]) 36 | 37 | return _ret 38 | 39 | 40 | if __name__ == '__main__': 41 | print(devide_by2(233)) 42 | print(devide_by_base(233, 16)) 43 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/joseph_question.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/15/18 10:37 AM 4 | # @Author : Miracle Young 5 | # @File : joseph_question.py 6 | 7 | 8 | from python_data_structure.base_data_structure.queue import Queue 9 | 10 | 11 | def joseph_question(roll_list, num): 12 | _q = Queue() 13 | for _item in roll_list: 14 | _q.enqueue(_item) 15 | 16 | while _q.size() > 1: 17 | for _ in range(num): 18 | _q.enqueue(_q.dequeue()) 19 | 20 | _q.dequeue() 21 | 22 | return _q.dequeue() 23 | 24 | 25 | if __name__ == '__main__': 26 | print(joseph_question(["Bill", "David", "Susan", "Jane", "Kent", "Brad"], 7)) -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/plaindrome.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/15/18 2:09 PM 4 | # @Author : Miracle Young 5 | # @File : plaindrome.py 6 | 7 | 8 | from python_data_structure.base_data_structure.deque import Deque 9 | 10 | 11 | def plaindrome(s): 12 | _deque = Deque() 13 | for _char in s: 14 | _deque.add_front(_char) 15 | 16 | _ok = True 17 | while _deque.size() > 1 and _ok: 18 | _front_char = _deque.remove_front() 19 | _rear_char = _deque.remove_rear() 20 | if not _front_char == _rear_char: 21 | _ok = False 22 | 23 | return _ok 24 | 25 | 26 | if __name__ == '__main__': 27 | print(plaindrome('roor')) 28 | print(plaindrome('rooor')) 29 | print(plaindrome('roofor')) 30 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/postfix.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 3:34 PM 4 | # @Author : Miracle Young 5 | # @File : postfix.py 6 | 7 | 8 | import string 9 | 10 | from python_data_structure.base_data_structure.stack import Stack 11 | 12 | 13 | def infix2prefix(s: str): 14 | _priority = { 15 | '*': 3, 16 | '/': 3, 17 | '+': 2, 18 | '-': 2, 19 | '(': 1, 20 | } 21 | _ret = [] 22 | _opstack = Stack() 23 | _srclst = s.split() 24 | _refer = string.ascii_uppercase + string.digits 25 | _index = 0 26 | while _index < len(_srclst): 27 | _item = _srclst[_index] 28 | if _item == '(': 29 | _opstack.push(_item) 30 | elif _item in _refer: 31 | _ret.append(_item) 32 | elif _item == ')': 33 | _top = _opstack.pop() 34 | # maybe exist multi operations rather than one. 35 | # so need to add continually until meet '(' 36 | while _top != '(': 37 | _ret.append(_top) 38 | _top = _opstack.pop() 39 | else: 40 | while (not _opstack.is_empty()) and _priority[_opstack.peek()] >= _priority[_item]: 41 | _ret.append(_opstack.pop()) 42 | _opstack.push(_item) 43 | _index += 1 44 | 45 | while not _opstack.is_empty(): 46 | _ret.append(_opstack.pop()) 47 | 48 | return ''.join(_ret) 49 | 50 | 51 | def postfix_math(s: str): 52 | _stack = Stack() 53 | _srclst = s.split() 54 | _refer = string.digits 55 | for _item in _srclst: 56 | if _item in _refer: 57 | _stack.push(int(_item)) 58 | else: 59 | _op1 = int(_stack.pop()) 60 | _op2 = int(_stack.pop()) 61 | # op2 operator op1 62 | _value = calc(_item, _op2, _op1) 63 | _stack.push(_value) 64 | 65 | return _stack.pop() 66 | 67 | 68 | def calc(op, n1, n2): 69 | if op == '+': 70 | return n1 + n2 71 | elif op == '-': 72 | return n1 - n2 73 | elif op == '*': 74 | return n1 * n2 75 | else: 76 | return n1 / n2 77 | 78 | 79 | if __name__ == '__main__': 80 | print(infix2prefix('( A + B ) * ( C + D )')) 81 | print(infix2prefix('( A + B ) * C')) 82 | print(infix2prefix('A + B * C')) 83 | print(postfix_math('7 8 + 3 2 + /')) 84 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/printer_queue.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/15/18 11:29 AM 4 | # @Author : Miracle Young 5 | # @File : printer_queue.py 6 | 7 | 8 | import random 9 | 10 | from python_data_structure.base_data_structure.queue import Queue 11 | 12 | 13 | class Task: 14 | def __init__(self, init_ts): 15 | # create task time 16 | self._init_ts = init_ts 17 | self._pages = random.randrange(1, 21) 18 | 19 | def get_stamp(self): 20 | return self._init_ts 21 | 22 | def get_pages(self): 23 | return self._pages 24 | 25 | # time to wait to execute print 26 | def wait_time(self, current_time): 27 | return current_time - self._init_ts 28 | 29 | @classmethod 30 | def new_task(cls): 31 | _num = random.randrange(1, 181) 32 | return _num == 180 33 | 34 | 35 | class Printer: 36 | def __init__(self, pagerate): 37 | # 60s can do how many tasks 38 | self._pagerate = pagerate 39 | self._current_task = None 40 | # current time, printer need times to finish job 41 | self._time_remaining = 0 42 | 43 | # simulate task working 44 | def tick(self): 45 | if self._current_task is not None: 46 | self._time_remaining -= 1 47 | if self._time_remaining <= 0: 48 | self._current_task = None 49 | 50 | def busy(self): 51 | return self._current_task is not None 52 | 53 | # execute next job in the queue 54 | def start_next(self, new_task: Task): 55 | self._current_task = new_task 56 | self._time_remaining = self._current_task.get_pages() * 60 / self._pagerate 57 | 58 | 59 | def simulation(total_seconds, pagerate): 60 | # init a printer 61 | _printer = Printer(pagerate) 62 | _task_queue = Queue() 63 | # store total time that all tasks waiting time 64 | _wait_time = [] 65 | 66 | # _current_second to record init time 67 | for _current_second in range(total_seconds): 68 | if Task.new_task(): 69 | # init one task, record init time 70 | _task = Task(_current_second) 71 | _task_queue.enqueue(_task) 72 | 73 | if (not _printer.busy()) and (not _task_queue.is_empty()): 74 | _next_task = _task_queue.dequeue() 75 | _wait_time.append(_next_task.wait_time(_current_second)) 76 | _printer.start_next(_next_task) 77 | 78 | _printer.tick() 79 | 80 | _avg_time = sum(_wait_time) / len(_wait_time) 81 | print(f"Average Wait {_avg_time:6.2f} secs {_task_queue.size():3d} tasks remaining.") 82 | 83 | 84 | if __name__ == '__main__': 85 | for _ in range(10): 86 | simulation(3600, 10) 87 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/queue.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/15/18 10:25 AM 4 | # @Author : Miracle Young 5 | # @File : queue.py 6 | 7 | 8 | class Queue: 9 | def __init__(self): 10 | self._items = [] 11 | 12 | def enqueue(self, item): 13 | self._items.insert(0, item) 14 | 15 | def dequeue(self): 16 | return self._items.pop() 17 | 18 | def is_empty(self): 19 | return self._items == [] 20 | 21 | def size(self): 22 | return len(self._items) 23 | 24 | 25 | -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/stack.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/14/18 11:14 AM 4 | # @Author : Miracle Young 5 | # @File : stack.py 6 | 7 | class Stack: 8 | def __init__(self): 9 | self._items = [] 10 | 11 | def is_empty(self): 12 | return self._items == [] 13 | 14 | def push(self, item): 15 | self._items.append(item) 16 | 17 | def pop(self): 18 | return self._items.pop() 19 | 20 | def peek(self): 21 | return self._items[len(self._items) - 1] 22 | 23 | def size(self): 24 | return len(self._items) -------------------------------------------------------------------------------- /python_data_structure/base_data_structure/unorderlist_orderlist.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/15/18 3:24 PM 4 | # @Author : Miracle Young 5 | # @File : unorderlist.py 6 | 7 | 8 | class Node: 9 | def __init__(self, data): 10 | self._data = data 11 | self._next = None 12 | 13 | def get_data(self): 14 | return self._data 15 | 16 | def get_next(self): 17 | return self._next 18 | 19 | def set_data(self, data): 20 | self._data = data 21 | 22 | def set_next(self, data): 23 | self._next = data 24 | 25 | 26 | class UnOrderList: 27 | def __init__(self): 28 | self._head = None 29 | 30 | def is_empty(self): 31 | return self._head is None 32 | 33 | def add(self, data): 34 | _node = Node(data) 35 | _node.set_next(self._head) 36 | self._head = _node 37 | 38 | def size(self): 39 | _current = self._head 40 | _count = 0 41 | while _current is not None: 42 | _current = _current.get_next() 43 | _count += 1 44 | return _count 45 | 46 | def search(self, data): 47 | _current = self._head 48 | _found = False 49 | 50 | while _current is not None and not _found: 51 | if _current.get_data() == data: 52 | _found = True 53 | else: 54 | _current = _current.get_next() 55 | 56 | return _found 57 | 58 | def remove(self, data): 59 | _current, _previous = self._head, None 60 | _found = False 61 | # find which one shoule be removed 62 | while _current is not None and not _found: 63 | if _current.get_data() == data: 64 | _found = True 65 | else: 66 | _previous = _current 67 | _current = _current.get_next() 68 | # remove the target node 69 | if _previous is None: 70 | self._head = _current.get_next() 71 | else: 72 | _previous.set_next(_current.get_next()) 73 | 74 | 75 | class OrderList: 76 | def __init__(self): 77 | self._head = None 78 | 79 | def is_empty(self): 80 | return self._head is None 81 | 82 | def size(self): 83 | _current = self._head 84 | _count = 0 85 | 86 | while _current is not None: 87 | _current = _current.get_next() 88 | _count += 1 89 | 90 | return _count 91 | 92 | def remove(self, data): 93 | _current, _previous = self._head, None 94 | _found = False 95 | 96 | while _current is not None and not _found: 97 | if _current.get_data() == data: 98 | _found = True 99 | else: 100 | _previous = _current 101 | _current = _current.get_next() 102 | 103 | if _previous is None: 104 | self._head = _current.get_next() 105 | else: 106 | _previous.set_next(_current.get_next()) 107 | 108 | def search(self, data): 109 | _current = self._head 110 | _found, _stop = False, False 111 | 112 | while _current is not None and not _found and not _stop: 113 | if _current.get_data() == data: 114 | _found = True 115 | elif _current.get_data() > data: 116 | _stop = True 117 | else: 118 | _current = _current.get_next() 119 | 120 | return _found 121 | 122 | def add(self, data): 123 | _current, _previous = self._head, None 124 | _stop = False 125 | 126 | while _current is not None and not _stop: 127 | if _current.get_data() > data: 128 | _stop = True 129 | else: 130 | _previous = _current 131 | _current = _current.get_next() 132 | 133 | _node = Node(data) 134 | if _previous is None: 135 | _node.set_next(self._head) 136 | self._head = _node 137 | else: 138 | _node.set_next(_current) 139 | _previous.set_next(_node) 140 | -------------------------------------------------------------------------------- /python_data_structure/graph/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/27/18 1:47 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/graph/bfs.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/27/18 2:39 PM 4 | # @Author : Miracle Young 5 | # @File : bfs.py 6 | 7 | 8 | from python_data_structure.graph.graphs import Graph, Vertex 9 | from python_data_structure.base_data_structure.queue import Queue 10 | 11 | 12 | def bfs(g: Graph, start: Vertex): 13 | start.set_distance(0) 14 | start.set_pred(None) 15 | _vert_queue = Queue() 16 | _vert_queue.enqueue(start) 17 | while _vert_queue.size() > 0: 18 | _current_vert = _vert_queue.dequeue() 19 | for _nbr in _current_vert.get_connections(): 20 | if _nbr.get_color() == 'white': 21 | _nbr.set_color('gray') 22 | _nbr.set_distance(_current_vert.get_distance() + 1) 23 | _nbr.set_pred(_current_vert) 24 | _vert_queue.enqueue(_nbr) 25 | _current_vert.set_color('black') 26 | -------------------------------------------------------------------------------- /python_data_structure/graph/graphs.py: -------------------------------------------------------------------------------- 1 | class Vertex: 2 | def __init__(self, key): 3 | self._id = key 4 | self._connected_to = {} 5 | 6 | def add_neighbor(self, nbr, weight=0): 7 | self._connected_to[nbr] = weight 8 | 9 | def __str__(self): 10 | return str(self._id) + ' connected to :' + str([x._id for x in self._connected_to]) 11 | 12 | def get_connections(self): 13 | return self._connected_to.keys() 14 | 15 | def get_id(self): 16 | return self._id 17 | 18 | def get_weight(self, nbr): 19 | return self._connected_to[nbr] 20 | 21 | def get_color(self): 22 | pass 23 | 24 | def set_color(self, color): 25 | pass 26 | 27 | def get_distance(self): 28 | pass 29 | 30 | def set_distance(self, distance): 31 | pass 32 | 33 | def set_pred(self, value): 34 | pass 35 | 36 | def predecessor(self): 37 | pass 38 | 39 | def color(self): 40 | pass 41 | 42 | 43 | class Graph: 44 | def __init__(self): 45 | self._vertex_list = {} 46 | self._num_vertex = 0 47 | 48 | def add_vertex(self, key): 49 | self._num_vertex += 1 50 | _new_vertex = Vertex(key) 51 | self._vertex_list[key] = _new_vertex 52 | return _new_vertex 53 | 54 | def get_vertex(self, key): 55 | return self._vertex_list[key] if key in self._vertex_list else None 56 | 57 | def __contains__(self, item): 58 | return item in self._vertex_list 59 | 60 | def add_edge(self, f, t, cost=0): 61 | if f not in self._vertex_list: 62 | self.add_vertex(f) 63 | if t not in self._vertex_list: 64 | self.add_vertex(t) 65 | self._vertex_list[f].add_neighbor(self._vertex_list[t], cost) 66 | 67 | def get_vertices(self): 68 | return self._vertex_list.keys() 69 | 70 | def __iter__(self): 71 | return iter(self._vertex_list.values()) 72 | 73 | 74 | if __name__ == '__main__': 75 | g = Graph() 76 | for i in range(6): 77 | g.add_vertex(i) 78 | 79 | print(g._vertex_list) 80 | 81 | g.add_edge(0, 1, 5) 82 | g.add_edge(0, 5, 2) 83 | g.add_edge(1, 2, 4) 84 | g.add_edge(2, 3, 9) 85 | g.add_edge(3, 4, 7) 86 | g.add_edge(3, 5, 3) 87 | g.add_edge(4, 0, 1) 88 | g.add_edge(5, 4, 8) 89 | g.add_edge(5, 2, 1) 90 | 91 | for v in g: 92 | for w in v.get_connections(): 93 | print("( %s , %s )" % (v.get_id(), w.get_id())) 94 | -------------------------------------------------------------------------------- /python_data_structure/graph/word_ladder.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/27/18 2:02 PM 4 | # @Author : Miracle Young 5 | # @File : word_ladder.py 6 | 7 | from python_data_structure.graph.graphs import Graph 8 | 9 | 10 | def build_graph(word_file): 11 | _d = {} 12 | _g = Graph() 13 | _wfile = open(word_file, 'r') 14 | for _line in _wfile: 15 | _word = _line[:-1] 16 | for i in range(len(_word)): 17 | _bucket = _word[:i] + '_' + _word[i + 1:] 18 | if _bucket in _d: 19 | _d[_bucket].append(_word) 20 | else: 21 | _d[_bucket] = _word 22 | for _bucket in _d.keys(): 23 | for w1 in _d[_bucket]: 24 | for w2 in _d[_bucket]: 25 | if w1 != w2: 26 | _g.add_edge(w1, w2) 27 | 28 | return _g 29 | -------------------------------------------------------------------------------- /python_data_structure/recursion/Sierpinski.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/17 下午4:42 4 | # @Author : MiracleYoung 5 | # @File : Sierpinski.py 6 | 7 | 8 | import turtle 9 | 10 | 11 | def draw_triangle(points, color, turtle: turtle.Turtle): 12 | turtle.fillcolor(color) 13 | turtle.up() 14 | turtle.goto(points[0][0], points[0][1]) 15 | turtle.down() 16 | turtle.begin_fill() 17 | turtle.goto(points[1][0], points[1][1]) 18 | turtle.goto(points[2][0], points[2][1]) 19 | turtle.goto(points[0][0], points[0][1]) 20 | turtle.end_fill() 21 | 22 | 23 | def get_mid(p1, p2): 24 | return (p1[0] + p2[0]) / 2, (p1[1] + p2[1]) / 2 25 | 26 | 27 | def sierpinski(points, degree, turtle: turtle.Turtle): 28 | _color_map = ['blue', 'red', 'green', 'white', 'yellow', 'violet', 'orange'] 29 | draw_triangle(points, _color_map[degree], turtle) 30 | if degree > 0: 31 | sierpinski([points[0], get_mid(points[0], points[1]), get_mid(points[0], points[2])], degree - 1, turtle) 32 | sierpinski([points[1], get_mid(points[1], points[0]), get_mid(points[1], points[2])], degree - 1, turtle) 33 | sierpinski([points[2], get_mid(points[2], points[1]), get_mid(points[2], points[0])], degree - 1, turtle) 34 | 35 | def main(): 36 | _turtle = turtle.Turtle() 37 | _screen = turtle.Screen() 38 | _points = [[-100, -50], [0, 100], [100, -50]] 39 | sierpinski(_points, 3, _turtle) 40 | _screen.exitonclick() 41 | 42 | main() -------------------------------------------------------------------------------- /python_data_structure/recursion/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/17 下午3:10 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/recursion/change_coins.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/19/18 2:45 PM 4 | # @Author : Miracle Young 5 | # @File : change_coins.py 6 | 7 | 8 | def change_coins(coins: list, change: int): 9 | _min_coins = change 10 | if change in coins: 11 | return 1 12 | else: 13 | for _item in [c for c in coins if c <= change]: 14 | _counts = 1 + change_coins(coins, change - _item) 15 | if _counts < _min_coins: 16 | _min_coins = _counts 17 | return _min_coins 18 | 19 | 20 | def change_coins_v2(coins: list, change: int, result: list): 21 | _min_coins = change 22 | if change in coins: 23 | result[change] = 1 24 | return 1 25 | elif result[change] > 0: 26 | return result[change] 27 | else: 28 | for _item in [c for c in coins if c <= change]: 29 | _counts = 1 + change_coins_v2(coins, change - _item, result) 30 | if _counts < _min_coins: 31 | _min_coins = _counts 32 | result[change] = _min_coins 33 | return _min_coins 34 | 35 | 36 | def dp_change_coins(coins: list, change: int, min_coins: list): 37 | for _cents in range(change + 1): 38 | _counts = _cents 39 | for j in [c for c in coins if c <= _cents]: 40 | if min_coins[_cents - j] + 1 < _counts: 41 | _counts = min_coins[_cents - j] + 1 42 | min_coins[_cents] = _counts 43 | return min_coins[change] 44 | 45 | 46 | if __name__ == '__main__': 47 | print(dp_change_coins([1, 5, 10, 25], 63, [0] * 64)) 48 | -------------------------------------------------------------------------------- /python_data_structure/recursion/int2str.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/17 下午3:11 4 | # @Author : MiracleYoung 5 | # @File : int2str.py 6 | 7 | def int2str(num: int, base: int): 8 | _ref = '0123456789ABCDEF' 9 | if num < base: 10 | return _ref[num] 11 | else: 12 | return int2str(num // base, base) + _ref[num % base] 13 | 14 | 15 | from python_data_structure.base_data_structure.stack import Stack 16 | 17 | 18 | def int2str_by_stack(num: int, base: int): 19 | _stack = Stack() 20 | _ref = '0123456789ABCDEF' 21 | while num > 0: 22 | if num < base: 23 | _stack.push(_ref[num]) 24 | else: 25 | _stack.push(_ref[num % base]) 26 | num //= base 27 | 28 | _ret = '' 29 | while not _stack.is_empty(): 30 | _ret += str(_stack.pop()) 31 | 32 | return _ret 33 | 34 | 35 | if __name__ == '__main__': 36 | print(int2str(2748, 16)) 37 | print(int2str_by_stack(2748, 16)) 38 | -------------------------------------------------------------------------------- /python_data_structure/recursion/maze.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/19/18 11:10 AM 4 | # @Author : Miracle Young 5 | # @File : maze.py 6 | 7 | 8 | import turtle 9 | 10 | PART_OF_PATH = 'O' 11 | TRIED = '.' 12 | OBSTACLE = '+' 13 | DEAD_END = '-' 14 | 15 | 16 | def search_from(maze, start_row, start_column): 17 | maze.updatePosition(start_row, start_column) 18 | if maze[start_row][start_column] == OBSTACLE: 19 | return False 20 | 21 | if maze[start_row][start_column] == TRIED: 22 | return False 23 | 24 | if maze.isExit(start_row, start_column): 25 | maze.updatePosition(start_row, start_column, PART_OF_PATH) 26 | return True 27 | maze.updatePosition(start_row, start_column, TRIED) 28 | 29 | # Otherwise, use logical short circuiting to try each 30 | # direction in turn (if needed) 31 | found = search_from(maze, start_row - 1, start_column) or \ 32 | search_from(maze, start_row + 1, start_column) or \ 33 | search_from(maze, start_row, start_column - 1) or \ 34 | search_from(maze, start_row, start_column + 1) 35 | if found: 36 | maze.updatePosition(start_row, start_column, PART_OF_PATH) 37 | else: 38 | maze.updatePosition(start_row, start_column, DEAD_END) 39 | return found 40 | 41 | 42 | class Maze: 43 | def __init__(self, maze_file): 44 | self._mazelist = [] 45 | for _r, _line in enumerate(open(maze_file, 'r')): 46 | _rowlist = [] 47 | for _j, _ch in enumerate(_line[:-1]): 48 | _rowlist.append(_ch) 49 | if _ch == 'S': 50 | self._start_row = _r 51 | self._start_col = _j 52 | 53 | self._mazelist.append(_rowlist) 54 | _rows_in_maze = _r 55 | _cols_in_maze = len(_rowlist) 56 | 57 | self._rows_in_maze = _rows_in_maze 58 | self._cols_in_maze = _cols_in_maze 59 | self._x = _cols_in_maze / 2 60 | self._y = _rows_in_maze / 2 61 | self._turtle = turtle.Turtle(shape='turtle') 62 | self._wn = turtle.Screen() 63 | 64 | self._wn.set_world_coordinates(-(_cols_in_maze - 1) / 2 - .5, 65 | -(_rows_in_maze - 1) / 2 - .5, 66 | (_cols_in_maze - 1) / 2 + .5, 67 | (_rows_in_maze - 1) / 2 + .5) 68 | 69 | def draw_maze(self): 70 | for _r in range(self._rows_in_maze): 71 | for _j in range(self._cols_in_maze): 72 | if self._mazelist[_r][_j] == OBSTACLE: 73 | self.draw_center_box(_j + self._x, -_r + self._y, 'tan') 74 | self._turtle.color('black', 'blue') 75 | 76 | def draw_center_box(self, x, y, color): 77 | self._turtle.up() 78 | self._turtle.goto(x - .5, y - .5) 79 | self._turtle.color('black', color) 80 | self._turtle.setheading(90) 81 | self._turtle.down() 82 | self._turtle.begin_fill() 83 | for _i in range(4): 84 | self._turtle.forward(1) 85 | self._turtle.right(90) 86 | self._turtle.end_fill() 87 | 88 | def move_turtle(self, x, y): 89 | self._turtle.up() 90 | self._turtle.setheading(self._turtle.towards(x + self._x, y + self._y)) 91 | self._turtle.goto(x + self._x, -y + self._y) 92 | 93 | def drop_breadcrumb(self, color): 94 | self._turtle.dot(color) 95 | 96 | def update_position(self, row, col, val=None): 97 | if val: 98 | self._mazelist[row][col] = val 99 | self.move_turtle(col, row) 100 | 101 | if val == PART_OF_PATH: 102 | _color = 'green' 103 | elif val == OBSTACLE: 104 | _color = 'red' 105 | elif val == TRIED: 106 | _color = 'black' 107 | elif val == DEAD_END: 108 | _color = 'red' 109 | else: 110 | _color = None 111 | 112 | if _color: 113 | self.drop_breadcrumb(_color) 114 | 115 | def is_exit(self, row, col): 116 | return (row == 0 117 | or row == self._rows_in_maze - 1 118 | or col == 0 119 | or col == self._cols_in_maze - 1) 120 | 121 | def __getitem__(self, item): 122 | return self._mazelist[item] 123 | 124 | myMaze = Maze('maze_sample.txt') 125 | myMaze.draw_maze() 126 | myMaze.update_position(myMaze._start_row,myMaze._start_col) 127 | 128 | search_from(myMaze, myMaze._start_row, myMaze._start_col) -------------------------------------------------------------------------------- /python_data_structure/recursion/maze_sample.txt: -------------------------------------------------------------------------------- 1 | ++++++++++++++++++++++ 2 | + + ++ ++ + 3 | + + + +++ + ++ 4 | + + + ++ ++++ + ++ 5 | +++ ++++++ +++ + + 6 | + ++ ++ + 7 | +++++ ++++++ +++++ + 8 | + + +++++++ + + 9 | + +++++++ S + + 10 | + + +++ 11 | ++++++++++++++++++ +++ -------------------------------------------------------------------------------- /python_data_structure/recursion/tower.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/17 下午5:48 4 | # @Author : MiracleYoung 5 | # @File : tower.py 6 | 7 | 8 | def move_tower(height,fromPole, toPole, withPole): 9 | if height >= 1: 10 | move_tower(height-1,fromPole,withPole,toPole) 11 | move_disk(fromPole,toPole) 12 | move_tower(height-1,withPole,toPole,fromPole) 13 | 14 | def move_disk(fp,tp): 15 | print("moving disk from",fp,"to",tp) 16 | 17 | 18 | move_tower(6, 'A', 'C', 'B') -------------------------------------------------------------------------------- /python_data_structure/recursion/tree.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/17 下午4:00 4 | # @Author : MiracleYoung 5 | # @File : tree.py 6 | 7 | import turtle 8 | 9 | def tree(turtle: turtle.Turtle, len): 10 | if len > 5: 11 | turtle.forward(len) 12 | turtle.right(20) 13 | tree(turtle, len - 15) 14 | turtle.left(40) 15 | tree(turtle, len - 10) 16 | turtle.right(20) 17 | turtle.backward(len) 18 | 19 | 20 | def main(): 21 | _turtle = turtle.Turtle() 22 | _screen = turtle.Screen() 23 | _turtle.left(90) 24 | _turtle.up() 25 | _turtle.backward(100) 26 | _turtle.down() 27 | _turtle.color('green') 28 | tree(_turtle, 75) 29 | _screen.exitonclick() 30 | 31 | main() -------------------------------------------------------------------------------- /python_data_structure/recursion/visualization.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/17 下午3:45 4 | # @Author : MiracleYoung 5 | # @File : visualization.py 6 | 7 | 8 | import turtle 9 | 10 | _turtle = turtle.Turtle() 11 | _screen = turtle.Screen() 12 | 13 | def draw_spiral(turtle: turtle.Turtle, len): 14 | if len > 0: 15 | turtle.forward(len) 16 | turtle.right(90) 17 | draw_spiral(turtle, len - 5) 18 | 19 | 20 | draw_spiral(_turtle, 100) 21 | _screen.exitonclick() 22 | -------------------------------------------------------------------------------- /python_data_structure/sort_find/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/20/18 11:27 AM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/sort_find/bubble_sort.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 上午7:37 4 | # @Author : MiracleYoung 5 | # @File : bubble_sort.py 6 | 7 | 8 | def bubble_sort(lst: list): 9 | for _n in range(len(lst) - 1, 0, -1): 10 | for _i in range(_n): 11 | if lst[_i] > lst[_i + 1]: 12 | lst[_i], lst[_i + 1] = lst[_i + 1], lst[_i] 13 | return lst 14 | 15 | 16 | def short_bubble_sort(lst: list): 17 | _n = len(lst) - 1 18 | _exchange = True 19 | while _n > 0 and _exchange: 20 | _exchange = False 21 | for _i in range(_n): 22 | if lst[_i] > lst[_i + 1]: 23 | _exchange = True 24 | lst[_i], lst[_i + 1] = lst[_i + 1], lst[_i] 25 | 26 | _n -= 1 27 | return lst 28 | 29 | 30 | if __name__ == '__main__': 31 | lst = [54, 26, 93, 17, 77, 31, 44, 55, 20] 32 | lst2= [20,30,40,90,50,60,70,80,100,110] 33 | print(bubble_sort(lst)) 34 | print(short_bubble_sort(lst2)) 35 | -------------------------------------------------------------------------------- /python_data_structure/sort_find/hash_find.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/20/18 2:48 PM 4 | # @Author : Miracle Young 5 | # @File : hash_sort.py 6 | 7 | 8 | def hash_find(ascii_str, slot): 9 | _sum = 0 10 | for _s in ascii_str: 11 | _sum += ord(_s) 12 | return _sum % slot 13 | 14 | 15 | class HashTable: 16 | def __init__(self): 17 | self._size = 11 18 | self.slots = [None] * self._size 19 | self.data = [None] * self._size 20 | 21 | def put(self, key, value): 22 | _hash = self._hash(key, len(self.slots)) 23 | if self.slots[_hash] == None: 24 | self.slots[_hash] = key 25 | self.data[_hash] = value 26 | else: 27 | if self.slots[_hash] == key: 28 | self.data[_hash] = value 29 | else: 30 | _nextslot = self._rehash(_hash, len(self.slots)) 31 | while self.slots[_nextslot] != None and self.slots[_nextslot] != key: 32 | _nextslot = self._rehash(_nextslot, len(self.slots)) 33 | 34 | if self.slots[_nextslot] == None: 35 | self.slots[_nextslot] = key 36 | self.data[_nextslot] = value 37 | else: 38 | self.data[_nextslot] = value 39 | 40 | def _hash(self, key, size): 41 | return key % size 42 | 43 | def _rehash(self, old_hash, size): 44 | return (old_hash + 1) % size 45 | 46 | def get(self, key): 47 | _startslot = self._hash(key, len(self.slots)) 48 | 49 | _data = None 50 | _stop, _found = False, False 51 | _pos = _startslot 52 | while self.slots[_pos] != None and not _stop and not _found: 53 | if self.slots[_pos] == key: 54 | _found = True 55 | _data = self.slots[_pos] 56 | else: 57 | _pos = self._rehash(_pos, len(self.slots)) 58 | if _pos == _startslot: 59 | _stop = True 60 | return _data 61 | 62 | def __getitem__(self, item): 63 | return self.get(item) 64 | 65 | def __setitem__(self, key, value): 66 | self.put(key, value) 67 | 68 | 69 | if __name__ == '__main__': 70 | print(hash_find('cat', 11)) 71 | -------------------------------------------------------------------------------- /python_data_structure/sort_find/insert_sort.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 上午8:13 4 | # @Author : MiracleYoung 5 | # @File : insert_sort.py 6 | 7 | 8 | def insert_sort(lst: list): 9 | for _i in range(1, len(lst)): 10 | _current_value = lst[_i] 11 | _idx = _i 12 | while _idx > 0 and lst[_idx - 1] > _current_value: 13 | lst[_idx] = lst[_idx - 1] 14 | _idx -= 1 15 | lst[_idx] = _current_value 16 | return lst 17 | 18 | 19 | if __name__ == '__main__': 20 | lst = [54,26,93,17,77,31,44,55,20] 21 | print(insert_sort(lst)) -------------------------------------------------------------------------------- /python_data_structure/sort_find/merge_sort.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 上午9:51 4 | # @Author : MiracleYoung 5 | # @File : merge_sort.py 6 | 7 | 8 | def merge_sort(lst: list): 9 | print(f'Splitting {lst}') 10 | if len(lst) > 1: 11 | _i, _j, _k = 0, 0, 0 12 | _mid = len(lst) // 2 13 | _lh, _rh = lst[:_mid], lst[_mid:] 14 | 15 | merge_sort(_lh) 16 | merge_sort(_rh) 17 | 18 | while _i < len(_lh) and _j < len(_rh): 19 | if _lh[_i] < _rh[_j]: 20 | lst[_k] = _lh[_i] 21 | _i += 1 22 | else: 23 | lst[_k] = _rh[_j] 24 | _j += 1 25 | _k += 1 26 | 27 | while _j < len(_rh): 28 | lst[_k] = _rh[_j] 29 | _j += 1 30 | _k += 1 31 | 32 | while _i < len(_lh): 33 | lst[_k] = _lh[_i] 34 | _i += 1 35 | _k += 1 36 | 37 | print(f'Merging {lst}') 38 | 39 | 40 | if __name__ == '__main__': 41 | lst = [54,26,93,17,77,31,44,55,20] 42 | print(merge_sort(lst)) -------------------------------------------------------------------------------- /python_data_structure/sort_find/quick_sort.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 下午2:29 4 | # @Author : MiracleYoung 5 | # @File : quick_sort.py 6 | 7 | 8 | def quick_sort(lst: list): 9 | quick_sort_helper(lst, 0, len(lst) - 1) 10 | 11 | 12 | def quick_sort_helper(lst: list, first: int, last: int): 13 | if first < last: 14 | _pivot = partition(lst, first, last) 15 | 16 | # left sublist 17 | quick_sort_helper(lst, first, _pivot - 1) 18 | # right sublist 19 | quick_sort_helper(lst, _pivot + 1, last) 20 | 21 | print(lst) 22 | 23 | 24 | def partition(lst: list, first: int, last: int): 25 | _left_mark, _right_mark = first + 1, last 26 | _pivot = lst[first] 27 | _done = False 28 | 29 | while not _done: 30 | while _left_mark <= _right_mark and lst[_left_mark] <= _pivot: 31 | _left_mark += 1 32 | 33 | while _right_mark >= _left_mark and lst[_right_mark] >= _pivot: 34 | _right_mark -= 1 35 | 36 | if _left_mark > _right_mark: 37 | _done = True 38 | else: 39 | lst[_left_mark], lst[_right_mark] = lst[_right_mark], lst[_left_mark] 40 | 41 | lst[first], lst[_right_mark] = lst[_right_mark], lst[first] 42 | 43 | return _right_mark 44 | 45 | 46 | 47 | if __name__ == '__main__': 48 | lst = [54,26,93,17,77,31,44,55,20] 49 | quick_sort(lst) 50 | -------------------------------------------------------------------------------- /python_data_structure/sort_find/select_sort.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 上午7:59 4 | # @Author : MiracleYoung 5 | # @File : select_sort.py 6 | 7 | 8 | def select_sort(lst: list): 9 | _pos_max = 0 10 | for _n in range(len(lst) -1, 0, -1): 11 | for _i in range(_n): 12 | if lst[_i] > lst[_pos_max]: 13 | _pos_max = _i 14 | lst[_pos_max], lst[_n] = lst[_n], lst[_pos_max] 15 | 16 | return lst 17 | 18 | 19 | if __name__ == '__main__': 20 | lst = [54,26,93,17,77,31,44,55,20] 21 | print(select_sort(lst)) -------------------------------------------------------------------------------- /python_data_structure/sort_find/sequential_search.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/20/18 11:29 AM 4 | # @Author : Miracle Young 5 | # @File : sequential_search.py 6 | 7 | def seq_search(lst: list, num: int): 8 | _pos = 0 9 | _found = False 10 | 11 | while _pos < len(lst) and not _found: 12 | if lst[_pos] == num: 13 | _found = True 14 | else: 15 | _pos += 1 16 | 17 | return _found 18 | 19 | 20 | def order_seq_search(lst: list, num: int) -> bool: 21 | _pos = 0 22 | _found = False 23 | _stop = False 24 | 25 | while _pos < len(lst) and not _found and not _stop: 26 | if lst[_pos] == num: 27 | _found = True 28 | elif lst[_pos] > num: 29 | _stop = True 30 | else: 31 | _pos += 1 32 | 33 | return _found 34 | 35 | 36 | def binary_search(lst: list, num: int) -> bool: 37 | _first, _last = 0, len(lst) - 1 38 | _found = False 39 | while _first <= _last and not _found: 40 | _mid = (_first + _last) // 2 41 | if lst[_mid] == num: 42 | _found = True 43 | elif lst[_mid] > num: 44 | _last = _mid - 1 45 | else: 46 | _first = _mid + 1 47 | 48 | return _found 49 | 50 | 51 | def binary_recursive_search(lst: list, num: int) -> bool: 52 | if len(lst) == 0: 53 | return False 54 | else: 55 | _mid = len(lst) // 2 56 | if lst[_mid] == num: 57 | return True 58 | elif lst[_mid] > num: 59 | return binary_recursive_search(lst[:_mid], num) 60 | else: 61 | return binary_recursive_search(lst[_mid + 1:], num) 62 | 63 | 64 | if __name__ == '__main__': 65 | _lst = [1, 2, 3, 5, 6, 12] 66 | print(seq_search(_lst, 123)) 67 | print(order_seq_search(_lst, 123)) 68 | print(binary_search(_lst, 5)) 69 | print(binary_recursive_search(_lst, 56)) 70 | -------------------------------------------------------------------------------- /python_data_structure/sort_find/shell_sort.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 上午9:18 4 | # @Author : MiracleYoung 5 | # @File : shell_sort.py 6 | 7 | 8 | def shell_sort(lst: list): 9 | _sublist_count = len(lst) // 2 10 | while _sublist_count > 0: 11 | for _start in range(_sublist_count): 12 | gap_insert(lst, _start, _sublist_count) 13 | 14 | print(f'After increments of size {_sublist_count}, The list is {lst}') 15 | 16 | _sublist_count //= 2 17 | 18 | 19 | def gap_insert(lst: list, start: int, gap: int): 20 | for _i in range(start + gap, len(lst), gap): 21 | _current_value = lst[_i] 22 | _pos = _i 23 | 24 | while _pos >= gap and lst[_pos - gap] > _current_value: 25 | lst[_pos] = lst[_pos - gap] 26 | _pos -= gap 27 | 28 | lst[_pos] = _current_value 29 | 30 | 31 | if __name__ == '__main__': 32 | lst = [54,26,93,17,77,31,44,55,20] 33 | print(shell_sort(lst)) -------------------------------------------------------------------------------- /python_data_structure/tree/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 下午3:18 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /python_data_structure/tree/binary_heap.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/25/18 10:54 AM 4 | # @Author : Miracle Young 5 | # @File : binary_heap.py 6 | 7 | class BinaryHeap: 8 | def __init__(self): 9 | self._heap_list = [] 10 | self._size = 0 11 | 12 | def perc_up(self, size): 13 | while size // 2 > 0: 14 | if self._heap_list[size] < self._heap_list[size // 2]: 15 | self._heap_list[size], self._heap_list[size // 2] = self._heap_list[size // 2], self._heap_list[size] 16 | size // 2 17 | 18 | def insert(self, i): 19 | self._heap_list.append(i) 20 | self._size += 1 21 | self.perc_up(self._size) 22 | 23 | def find_min(self, i): 24 | pass 25 | 26 | def perc_down(self, pos): 27 | while pos * 2 <= self._size: 28 | _mc = self.min_child(pos) 29 | if self._heap_list[pos] > self._heap_list[_mc]: 30 | self._heap_list[pos], self._heap_list[_mc] = self._heap_list[_mc], self._heap_list[pos] 31 | pos = _mc 32 | 33 | 34 | 35 | # find pos's max(maxchild, minchild) 36 | def min_child(self, pos): 37 | if pos * 2 + 1 > self._size: 38 | return pos * 2 39 | else: 40 | if self._heap_list[pos * 2] < self._heap_list[pos * 2 + 1]: 41 | return pos * 2 42 | else: 43 | return pos * 2 + 1 44 | 45 | def del_min(self): 46 | _del_val = self._heap_list[1] 47 | self._heap_list[1] = self._heap_list[self._size] 48 | self._size -= 1 49 | self._heap_list.pop() 50 | self.perc_down(1) 51 | return _del_val 52 | 53 | def is_empty(self): 54 | pass 55 | 56 | def size(self): 57 | pass 58 | 59 | def build_heap(self, lst): 60 | print(f'Start ordering... {lst}') 61 | _pos = len(lst) // 2 62 | self._size = len(lst) 63 | self._heap_list = [0] + lst 64 | while _pos > 0: 65 | self.perc_down(_pos) 66 | _pos -= 1 67 | print(f'List ordered: {self._heap_list}') 68 | 69 | 70 | if __name__ == '__main__': 71 | bh = BinaryHeap() 72 | bh.build_heap([9, 5, 6, 2, 3]) 73 | print(bh.del_min()) 74 | print(bh.del_min()) 75 | print(bh.del_min()) 76 | print(bh.del_min()) 77 | print(bh.del_min()) -------------------------------------------------------------------------------- /python_data_structure/tree/binary_tree.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 下午3:28 4 | # @Author : MiracleYoung 5 | # @File : binary_tree.py 6 | 7 | 8 | class BinaryTree: 9 | def __init__(self, root): 10 | self._key = root 11 | self._left = None 12 | self._right = None 13 | 14 | def insert_left(self, new_branch): 15 | if self._left: 16 | _t = BinaryTree(new_branch) 17 | _t._left = self._left 18 | self._left = _t 19 | else: 20 | self._left = BinaryTree(new_branch) 21 | 22 | def insert_right(self, new_branch): 23 | if self._right: 24 | _t = BinaryTree(new_branch) 25 | _t._right = self._right 26 | self._right = _t 27 | else: 28 | self._right = BinaryTree(new_branch) 29 | 30 | def get_right_child(self): 31 | return self._right 32 | 33 | def get_left_child(self): 34 | return self._left 35 | 36 | def set_root_val(self, val): 37 | self._key = val 38 | 39 | def get_root_val(self): 40 | return self._key 41 | 42 | def preorder(self): 43 | print(self._key) 44 | if self._left: 45 | self._left.preorder() 46 | if self._right: 47 | self._right.preorder() 48 | 49 | 50 | if __name__ == '__main__': 51 | r = BinaryTree('a') 52 | print(r.get_root_val()) 53 | print(r.get_left_child()) 54 | r.insert_left('b') 55 | print(r.get_left_child()) 56 | print(r.get_left_child().get_root_val()) 57 | r.insert_right('c') 58 | print(r.get_right_child()) 59 | print(r.get_right_child().get_root_val()) 60 | r.get_right_child().set_root_val('hello') 61 | print(r.get_right_child().get_root_val()) -------------------------------------------------------------------------------- /python_data_structure/tree/math_exp.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 下午3:58 4 | # @Author : MiracleYoung 5 | # @File : math_exp.py 6 | 7 | import operator 8 | 9 | from python_data_structure.base_data_structure.stack import Stack 10 | from python_data_structure.tree.binary_tree import BinaryTree 11 | 12 | def build_parse_tree(exp: str): 13 | _exp_list = exp.split() 14 | _stack = Stack() 15 | _tree = BinaryTree('') 16 | _stack.push(_tree) 17 | _current = _tree 18 | 19 | for _item in _exp_list: 20 | if _item == '(': 21 | _current.insert_left('') 22 | _stack.push(_current) 23 | _current = _current.get_left_child() 24 | elif _item in ['+', '-', '*', '/']: 25 | # set current node value 26 | _current.set_root_val(_item) 27 | _current.insert_right('') 28 | _stack.push(_current) 29 | _current = _current.get_right_child() 30 | # number 31 | elif _item not in ['+', '-', '*', '/', ')']: 32 | _current.set_root_val(int(_item)) 33 | _current = _stack.pop() 34 | elif _item == ')': 35 | _current = _stack.pop() 36 | else: 37 | raise ValueError 38 | return _tree 39 | 40 | 41 | def evaluate(tree: BinaryTree): 42 | _operators = {'+': operator.add, '-': operator.sub, '*': operator.mul, '/': operator.truediv} 43 | _left = tree.get_left_child() 44 | _right = tree.get_right_child() 45 | 46 | if _left and _right: 47 | _fn = _operators[tree.get_root_val()] 48 | return _fn(evaluate(_left), evaluate(_right)) 49 | else: 50 | return tree.get_root_val() 51 | 52 | 53 | if __name__ == '__main__': 54 | pt = build_parse_tree("( ( 10 + 5 ) * 3 )") 55 | print(evaluate(pt)) -------------------------------------------------------------------------------- /python_data_structure/tree/tree_list.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 下午3:18 4 | # @Author : MiracleYoung 5 | # @File : tree_list.py 6 | 7 | 8 | def binary_tree(root): 9 | return [root, [], []] 10 | 11 | 12 | def insert_left(root: list, new_branch): 13 | _t = root.pop(1) 14 | if len(_t) > 1: 15 | root.insert(1, [new_branch, _t, []]) 16 | else: 17 | root.insert(1, [new_branch, [], []]) 18 | return root 19 | 20 | 21 | def insert_right(root: list, new_branch): 22 | _t = root.pop(2) 23 | if len(_t) > 1: 24 | root.insert(2, [new_branch, [], _t]) 25 | else: 26 | root.insert(2, [new_branch, [], []]) 27 | return root 28 | 29 | 30 | def get_root_val(root): 31 | return root[0] 32 | 33 | 34 | def set_root_val(root, val): 35 | root[0] = val 36 | 37 | 38 | def get_left_child(root): 39 | return root[1] 40 | 41 | 42 | def get_right_child(root): 43 | return root[2] 44 | -------------------------------------------------------------------------------- /python_data_structure/tree/tree_traverse.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/24 下午5:03 4 | # @Author : MiracleYoung 5 | # @File : tree_traverse.py 6 | 7 | import operator 8 | 9 | from python_data_structure.tree.binary_tree import BinaryTree 10 | from python_data_structure.tree.math_exp import build_parse_tree 11 | 12 | 13 | def pre_order(tree: BinaryTree): 14 | if tree: 15 | print(tree.get_root_val()) 16 | pre_order(tree.get_left_child()) 17 | pre_order(tree.get_right_child()) 18 | 19 | 20 | def post_order(tree: BinaryTree): 21 | if tree: 22 | post_order(tree.get_left_child()) 23 | post_order(tree.get_right_child()) 24 | print(tree.get_root_val()) 25 | 26 | 27 | def post_order_eval(tree: BinaryTree): 28 | _operators = {'+': operator.add, '-': operator.sub, '*': operator.mul, '/': operator.truediv} 29 | if tree: 30 | _ret1 = post_order_eval(tree.get_left_child()) 31 | _ret2 = post_order_eval(tree.get_right_child()) 32 | if _ret1 and _ret2: 33 | return _operators[tree.get_root_val()](_ret1, _ret2) 34 | else: 35 | return tree.get_root_val() 36 | 37 | 38 | def in_order(tree: BinaryTree): 39 | if tree: 40 | in_order(tree.get_left_child()) 41 | print(tree.get_root_val()) 42 | in_order(tree.get_right_child()) 43 | 44 | 45 | def print_exp(tree: BinaryTree): 46 | _s = '' 47 | if tree: 48 | _s = '(' + print_exp(tree.get_left_child()) 49 | _s = _s + str(tree.get_root_val()) 50 | _s = _s + print_exp(tree.get_right_child()) + ')' 51 | return _s 52 | 53 | if __name__ == '__main__': 54 | pt = build_parse_tree("( ( 10 + 5 ) * 3 )") 55 | print(print_exp(pt)) -------------------------------------------------------------------------------- /spider/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/7/27 上午5:47 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /spider/sexual_assault.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/7/27 上午5:48 4 | # @Author : MiracleYoung 5 | # @File : sexual_assault.py 6 | 7 | -------------------------------------------------------------------------------- /tools/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/5/31 下午4:36 4 | # @Author : MiracleYoung 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /unit_test/__init__.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/6/18 12:04 PM 4 | # @Author : Miracle Young 5 | # @File : __init__.py.py 6 | -------------------------------------------------------------------------------- /unit_test/app.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # -*- coding: utf-8 -*- 3 | # @Time : 6/6/18 12:04 PM 4 | # @Author : Miracle Young 5 | # @File : app.py 6 | 7 | 8 | import requests 9 | 10 | headers = { 11 | "content-type": "application/json", 12 | "Host": "tapdata-server", 13 | "Origin": "http://tapdata-server", 14 | "Referer": "http://tapdata-server/login", 15 | "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/72.0.3626.96 Safari/537.36", 16 | } 17 | 18 | payload = { 19 | "username": "arthur@tapdata.io", 20 | "password": "123456", 21 | "options": { 22 | "device": {"platform": "chrome", "platformVersion": "72.0.3626", "sdkVersion": "4.1.1"} 23 | } 24 | } 25 | 26 | res = requests.request( 27 | method='POST', 28 | url='http://tapdata-server/api/client/v2.0/app/mongodb-charts-jgejk/auth/providers/local-userpass/login', 29 | data=payload, 30 | headers=headers 31 | ) 32 | print(res) 33 | -------------------------------------------------------------------------------- /unit_test/test2.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | # encoding: utf-8 3 | # @Time : 2018/6/25 上午6:04 4 | # @Author : MiracleYoung 5 | # @File : test2.py 6 | 7 | s = ''' 8 | 9 | 「运维发展路线」一个非常大的概念。这篇文章意在简单扼要的说明来龙去脉,若对某一点希望深挖下去,欢迎「提问」。我也会就某些值得探讨的问题作为以后的周课题进行研讨。以下内容均为小胖个人观点,有任何出入,欢迎「留言」或「提问」,一同探讨。 10 | 之所以本周要说这个,是因为几点: 11 | 1. 正好有球友前几天遇到了类似的困惑。 12 | 2. 我的同事在不久之前也向我请教过类似的问题。 13 | 3. 目前运维行业经过多年的发展,已经沉淀出了不同层级。如果不向上,则必将被趋势淹没。 14 | 15 | 什么是运维? 16 | 狭义定论:运行维护服务器。 17 | 广义定论:保障公司所有服务、业务、数据安全稳定的或对外或对内提供不间断的输出。 18 | 通俗点说,运维就是一座桥的扶手,平时不刮风走路不扶扶手甚至跑起来都可以。但是桥一旦出现了抖动、摇晃,你第一时间想到的就是去扶两边的扶手。 19 | 这就是工作中运维最常见到的景象,服务器不炸没事,一炸1分钟内背后就能排队和你抢空气吸。 20 | 我接触到的运维部门,大致可以分为:系统组(SRE/SA)、数据库组(DBA)、IT(Help Desk/桌面运维)、网络组(IDC)、监控组、安全组。 21 | 而系统组一般还可以细化:业务运维、基础运维、系统管理。 22 | 监控可以细化为:值班监控、一线运维、监控开发等。 23 | 这里我就不在一一举例说明了,感兴趣的,可以直接滑到最下面看「Mind」。 24 | 25 | 之前球友提出的问题是:自己做了多年的IT支持,现在只会Linux的基本命令和安装系统等,很迷茫,不知道自己以后怎么办,想做出改变。小胖在回答里已经说了一部分了,这里再补充些。 26 | 问题分两面性,IT本身的工作确实比较杂碎,我见过最多的就是拿着板车推来推去的给人换电脑,或者去进货,要么就是一直接电话解决电话打不通咯、网上不了咯、VPN断了咯等等。所以本身的知识面要求比较广,但是又不会要求深入某一Domain。 27 | 另一方面,如果真的想在IT这块深耕的话,还是有办法的,我说了,可以自己做一套桌面运维平台,提供基本的软件安装流程、订单系统、智能客服等等。智能客服的作用就是帮你解决80%的日常提问。这样看来还是有事情做的。 28 | 29 | 那回到今天的主题,我是从一家创业公司的运维开始做起,之后转型到DBA,再到现在的运维开发/架构。以后可能会继续去接触业务。 30 | 为什么会有这条线是非常重要的。我会在之后的主题中来单独讲这个。 31 | 32 | 运维从上古时代的人工救火 -> 脚本运维 -> 自动化运维 -> 智能运维,这无不体现了时代的发展带来的技术革新。无论从事什么行业的什么部门,我们都需要禀着一颗向上的心去面对、接受、拥抱它。否则趋势就会像天鸽一样所到之处,寸草不生。 33 | 34 | 换个角度看,运维本身也是一个需要面非常广的职位。你要懂操作系统(Centos、Ubuntu、BSD、WindowsServer),数据库(Oracle、MySQL、MSSQL、MongoDB、Redis、Hadoop系列等等),网络(交换机、VPN、硬件配置),更深入一个层次,可能需要会开发(自动化运维平台),或者数据库二次开发(针对公司业务场景,优化数据库源码)。而我们的职位只是对于某一个领域的纵深,但是其他也要懂,否则会成为我们的瓶颈。 35 | 36 | 那么今天主要是开了个头,可能会成为一个系列「运维发展路线」。 37 | 欢迎同行指出、矫正。 38 | ''' 39 | print(len(s)) 40 | --------------------------------------------------------------------------------