首页 文章 精选 留言 我的

精选列表

搜索[零点击],共10000篇文章
优秀的个人博客,低调大师

从零开始实现一个IDL+RPC框架

一、RPC是什么 在很久之前的单机时代,一台电脑中跑着多个进程,进程之间没有交流各干各的,就这样过了很多年。突然有一天有了新需求,A进程需要实现一个画图的功能,恰好邻居B进程已经有了这个功能,偷懒的程序员C想出了一个办法:A进程调B进程的画图功能。于是出现了IPC(Inter-process communication,进程间通信)。就这样程序员C愉快的去吃早餐去了! 又过了几年,到了互联网时代,每个电脑都实现了互联互通。这时候雇主又有了新需求,当时还没挂的A进程需要实现使用tensorflow识别出笑脸 >_< 。说巧不巧,远在几千里的一台快速运行的电脑上已经实现了这个功能,睡眼惺忪的程序媛D接手了这个A进程后借鉴之前IPC的实现,把IPC扩展到了互联网上,这就是RPC(Remote Procedure Call,远程过程调用)。RPC其实就是一台电脑上的进程调用另外一台电脑上的进程的工具。成熟的RPC方案大多数会具备服务注册、服务发现、熔断降级和限流等机制。目前市面上的RPC已经有很多成熟的了,比如Facebook家的Thrift、Google家的gRPC、阿里家的Dubbo和蚂蚁家的SOFA。 二、接口定义语言 接口定义语言,简称IDL,是实现端对端之间可靠通讯的一套编码方案。这里有涉及到传输数据的序列化和反序列化,我们常用的http的请求一般用json当做序列化工具,定制rpc协议的时候因为要求响应迅速等特点,所以大多数会定义一套序列化协议。比如: Protobuf: 讲到Protobuf就得讲到该库作者的另一个作品Cap'n proto了,号称性能是直接秒杀Google Protobuf,直接上官方对比: 虽然知道很多比Protobuf更快的编码方案,但是快到这种地步也是厉害了,为啥这么快,Cap’n Proto的文档里面就立刻说明了,因为Cap'n Proto没有任何序列号和反序列化步骤,Cap'n Proto编码的数据格式跟在内存里面的布局是一致的,所以可以直接将编码好的structure直接字节存放到硬盘上面。贴个栗子: 我们这里要定制的编码方案就是基于protobuf和Cap'n Proto结合的类似的语法。因为本人比较喜欢刀剑神域里的男主角,所以就给这个库起了个名字—— Kiritobuf。 首先我们定义kirito的语法: 开头的是注释 保留关键字, service、method、struct, {}里是一个块结构 ()里有两个参数,第一个是请求的参数结构,第二个是返回值的结构 @是定义参数位置的描述符,0表示在首位 =号左边是参数名,右边是参数类型 参数类型: Boolean: Bool Integers: Int8, Int16, Int32, Int64 Unsigned integers: UInt8, UInt16, UInt32, UInt64 Floating-point: Float32, Float64 Blobs: Text, Data Lists: List(T) 定义好了语法和参数类型,我们先过一下生成有抽象关系代码的流程: 取到.kirito后缀的文件,读取全部字符,通过词法分析器生成token,得到的token传入语法分析器生成AST (抽象语法树)。 首先我们新建一个kirito.js文件: 定义好了一些必要的字面量,接下来首先是词法分析阶段。 1、词法解析 我们设计词法分析得到的Token是这样子的: 词法分析步骤: 把获取到的kirito代码串按照n分割组合成数组A,数组的每个元素就是一行代码 遍历数组A,将每行代码逐个字符去读取 在读取的过程中定义匹配规则,比如注释、保留字、变量、符号、数组等 将每个匹配的字符或字符串按照对应类型添加到tokens数组中 代码如下: 2、语法分析 得到上面的词法分析的token后,我们就可以对该token做语法分析,我们需要最终生成的AST的格式如下: 看上图我们能友好的得到结构、参数、数据类型、函数之间的依赖和关系,步骤: 1、遍历词法分析得到的token数组,通过调用分析函数提取token之间的依赖节点 2、分析函数内部定义token提取规则,比如: 服务保留字 服务名 { 函数保留字 函数名 ( 入参,返回参数 ) } 参数结构保留字 结构名 { 参数位置 参数名 参数数据类型 }3、递归调用分析函数提取对应节点依赖关系,将节点添加到AST中 代码如下: 3、转换器 得到了语法分析的AST后我们需要进一步对AST转换为更易操作的js对象。格式如下: 通过上面这个格式,我们可以更容易的知道有几个service、service里有多少个函数以及函数的参数。 代码如下: 三、传输协议 RPC协议有多种,可以是json、xml、http2,相对于http1.x这种文本协议,http2.0这种二进制协议更适合作为RPC的应用层通信协议。很多成熟的RPC框架一般都会定制自己的协议已满足各种变化莫测的需求。 比如Thrift的TBinaryProtocol、TCompactProto-col等,用户可以自主选择适合自己的传输协议。(除了按字节编址还有按字编址和按位编址),我们这里只讨论字节编址。每个机器因为不同的系统或者不同的CPU对内存地址的编码有不一样的规则,一般分为两种字节序:大端序和小端序。 大端序: 数据的高字节保存在低地址 小端序: 数据的低字节保存在高地址 举个栗子: 比如一个整数:258,用16进制表示为0x0102,我们把它分为两个字节0x01和ox02,对应的二进制为0000 0001和0000 0010。在大端序的电脑上存放形式如下: 小端序则相反。为了保证在不同机器之间传输的数据是一样的,开发一个通讯协议时会首先约定好使用一种作为通讯方案。java虚拟机采用的是大端序。在机器上我们称为主机字节序,网络传输时我们称为网络字节序。网络字节序是TCP/IP中规定好的一种数据表示格式,它与具体的CPU类型、操作系统等无关,从而可以保证数据在不同主机之间传输时能够被正确解释。网络字节序采用大端排序方式。 我们这里就不造新应用层协议的轮子了,我们直接使用MQTT协议作为我们的默认应用层协议。MQTT(Message Queuing Telemetry Tran-sport,消息队列遥测传输协议),是一种基于发布/订阅(publish/subscribe)模式的“轻量级”通讯协议,采用大端序的网络字节序传输,该协议构建于TCP/IP协议上。 四、实现通讯 先贴下实现完的代码调用流程,首先是server端: client端: 无论是server端定义函数或者client端调用函数都是比较简洁的步骤。接下来我们慢慢剖析具体的逻辑实现。 贴下具体的调用流程架构图: 调用流程总结: client端解析kirito文件,绑定kirito的service到client对象 server端解析kirito文件,将kiritod的service与调用函数绑定添加到server对象 client端调用kirito service 里定义的函数,注册回调事件,发起MQTT请求 server端接收MQTT请求,解析请求body,调用对应的函数执行完后向client端发起MQTT请求 client端接收到MQTT请求后,解析body和error,并从回调事件队列里取出对应的回调函数并赋值执行 说完了调用流程,现在开始讲解具体的实现。 server: 定义protocol接口,加上这一层是为了以后的多协议,mqtt只是默认使用的协议: 接下来是server端的暴露出去的接口: client: 定义protocol接口: 最后是client端暴露的接口: 就这样,一个简单的IDL+RPC框架就这样搭建完成了。这里只是描述RPC的原理和常用的调用方式,要想用在企业级的开发上,还得加上服务发现、注册,服务熔断,服务降级等,读者如果有兴趣可以在Github上fork下来或者提PR来改进这个框架,有什么问题也可以提Issue, 当然PR是最好的 : ) 。 仓库地址: RPC: https://github.com/polixjs/polix-rpc IDL:https://github.com/rickyes/kiritobuf 更多文章请访问数澜社区,欢迎大家来一起学习~

优秀的个人博客,低调大师

适合Java零基础小白的学习思路与建议

如何准备转行学习Java,相信很多初学Java者都在考虑这个问题,如果你是在校学生,务必要在学好基础(比如计算机系统、算法、编译原理等等)的前提下,再考虑去进行下面的学习,第一部分:对于尚未做过Java工作的同学,包括一些在校生以及刚准备转行Java的同学。 一、Java基础首先去找一个Java基础教程学一下,这里推荐动力节点基础教学视频,学习Java基础的时候,应该尽量多动手,很多时候,你想当然的事情,等你写出来运行一下,你就会发现不是这么回事儿,不信你就试试,学完以上内容后,你应该对Java有一个基本的了解了,你可以用Java语言写出一些简单的程序,并且你用的是最简单的编辑器,比如记事本,这个时候,不要急于进入下一部分,留下几天好好写一些程序,尽可能熟悉这些基础内容。 二、Web开发等你写上几天程序以后,你往往会比较迷茫,因为你写的东西似乎看起来毫无用处,比如实现一个简单的计算器,读取一个文件等。这个时候你就应该去学着写一些让你觉得有意思的东西了,所以你应该学习更多的知识。这些内容主要是Web开发相关的内容,包括HTML/CSS/JS(前端页面)、Servlet/JSP(J2EE)以及Mysql(数据库)相关的知识。它们的学习顺序应该是从前到后,因此最先学习的应该是HTML/CSS/JS(前端页面) 你可以试着自己写一些页面,当然,你可以尽你最大的努力让它变得最漂亮。这部分内容对于后端Java来说,理论上不是特别重要,但至少要达到可以自己写出一些简单页面的水平。接下来,你需要学习的是Servlet/JSP(J2EE)部分,这部分是Java后端开发必须非常精通的部分,因此这部分是这三部分中最需要花精力的,而且这个时候,你要学会使用开发工具,而不能再使用记事本了,可以选择eclipse,当你下载安装好eclipse以后,看视频中的教程一步一步去学习,一定要多动手,关于Servlet/Jsp部分视频的选择,大家可以选择动力节点的。 最后一步,你需要学会使用数据库,mysql是个不错的入门选择,而且Java领域里主流的关系型数据库就是mysql。这部分一般在你学习Servlet/Jsp的时候,就会接触到的,其中的JDBC部分就是数据库相关的部分。你不仅要学会使用JDBC操作数据库,还要学会使用数据库客户端工具,比如navicat,sqlyog,二选一即可。 三、开发框架当你学会以上内容以后,这个时候你还不足以参加工作,你还需要继续深造。公司里为了提高开发的效率,会使用一些JavaWeb框架,因此你还需要学习一些开发框架。目前比较主流的是SSM框架,即spring、springmvc、mybatis。你需要学会这三个框架的搭建,并用它们做出一个简单的增删改查的Web项目。你可以不理解那些配置都是什么含义,以及为什么要这么做,这些留着后面你去了解。 但你一定要可以快速的利用它们三个搭建出一个Web框架,你可以记录下你第一次搭建的过程,相信自己,你一定会用到的。还要提一句的是,你在搭建SSM的过程中,可能会经常接触到一个叫maven的工具。这个工具也是你以后工作当中几乎是必须要使用的工具,所以你在搭建SSM的过程中,也可以顺便了解一下maven的知识。在你目前这个阶段,你只需要在网络上了解一下maven基本的使用方法即可,一些高端的用法随着你工作经验的增加,会逐渐接触到的。 四、当你完成开发框架的学习以后,你就该找工作了,在校的找实习,毕业的找全职。与此同时,在找工作的同时,你不应该停下你的学习,准确的说,是你在以后都不能停下学习,上面这些内容你只是囫囵吞枣的学会了使用,你可以逐步尝试着去了解更多的东西,网络是你最重要的老师,好了,说了这么多了,就到此为止吧,希望本文可以帮助到作为程序猿或即将成为程序猿的你。

优秀的个人博客,低调大师

非科班的 Java零基础系统学习路线

学习路线路线一以视频为主,视频能帮我们快速的进行实操,跟着老师走也基本不会有太大的错误,下面具体说下学习过程,按照先后顺序大概如下: Java方面:JavaSE,JavaWeb,JavaEE主流框架,大概就是Mybatis(最常用,灵活简便),Hibernate(这个好多公司都没用,重量级,学起来比较费力,容易头晕),Maven(开发必用),Spring,SpringMVC(现在开发的话基本就是Spring家族的天下了,可想而知其统治地位),git和svn(版本管理工具,git 愈发流行了。 数据库方面:MySQL,Oracle,Redis。MySQL是开源的关系型数据库,大部分公司用这个,Oracle收费的,银行用的比较多,二者都实现了标准的sql语句,推荐首先学习MySQL,一通百通,而且面试都是问MySQL,把它搞定就行了。Redis是最常用非关系型数据库,学起来比MySQL容易些,上手快。 分布式方面:Dubbo,SpringBoot,SpringCloud。分布式是未来发展的主流,dubbo以后也作为spring家族的一员专注远程调用这块。SpringCloud有一整套的微服务理念的落地实现,只能说很强! Linux,同学们记得做笔记啊,知识点很杂和多;Netty高性能网络框架,这块有时间可以看看视频,原理还是比较简单。 路线二以书籍为主,视频看完基本就再也不会看第二遍了,书本能让我们反复的去咀嚼,深挖其中的原理,从而记忆更牢固,一本好书能够让你学习起来更加轻松愉快,下面推荐的书籍都是我从各个渠道收集而来,口碑较好的书籍: 计算机基础方面:《计算机网络自顶向下方法》吐血力荐!书中从生活中的小事举例,形象生动,深入浅出,印象深刻,极易理解,本来网络这个东西就很抽现,看不见摸不着,选择他作为入门,我只能说或许你又快人一步了!《数据结构与算法》只要踏入这个行业,这个东西就必不可少,但凡说到原理,就是在谈这个东西,所以它的重要性是不言而喻的,而且面试笔试中也是必问的,答应我,好好学,好吗!(尽管我也学的很菜)《计算机组成原理》、《操作系统》这两本书开发中运用的比较少,但是非常有助于我们理解其底层运行机制和运行环境,当然如果你觉得一直搬砖也不错的话,略过。这四本书是计算机的基础,最好是能够多看几遍,对于后面的学习大有裨益。都是机械出版社,从外文翻译过来的,封面风格一致。 数据库方面:《高性能MySQL》这本书有点厚,知识点很全,适合作为工具书,《MySQL 技术内幕—InnoDB 存储引擎》此书讲的很底层,适合有一定基础的时候再看,但是个人觉得存储原理那块讲的特别好,有了此书,分分钟碾压面试官好嘛,《Redis设计与实现》讲的挺透的,但是个人对这本书没有太多的感觉,酱紫。 Java方面:《疯狂Java讲义》,《疯狂Java程序员的基本修养》作者李刚,这两本书比较基础,适合小白入门及查缺补漏,没事多翻翻,《Java编程思想》Java学习必读经典,不管是初学者还是大牛都值得一读,但是我还是罗嗦一句,小白慎入,有点厚,压力有点大,哈哈。《轻量级JavaEE应用实战》也是李刚的,这本书比较综合了,建议先看框架视频,然后再看书理解起来比较容易,这书不是一般的厚,厚到让你怀疑人生,仍记得从图书馆借出来后,旁人看我的异样眼光,这种书一般不用挨着看,挑重点。《深入理解Java虚拟机》Java高级程序员必经之路,对Java有着深入的剖析,开发中少用,但绝对值得细细品味,《Java多线程设计模式》可谓是Java中最让人头疼的一部分知识,但是又不得不学习,算是高级知识了,怎么说额,硬着头皮上吧。这些都是从事Java开发的必要知识,也是Java面试的重点。 算法方面:《程序员面试代码指南》左神的倾力之作,你离大神只有一本书的距离!《编程之美》和《剑指offer》程序员中几乎人手一本,你不买一本好意思说自己是程序员?把这三本书中的中等题刷完也完全足够对付面试和笔试中算法题了,别说手撕代码,手撕面试官都没有问题,好吗? 其他方面:《鸟哥的Linux私房菜》此书也是我的入门书籍,内容较多,适合当作工具书查阅,甚至被封为“linux入门神书”,不接受反驳。 路线三经常去各大网站都能够学习到很多东西,互联网学习需要你一种开放的心态,既要学会从中获取,也要学会给予。列下我经常去的几个:开源中国,csdn,牛客网,知乎,github,Stacoverflow。一路走来他们都有帮我解决了很多问题。我们都知道很多东西都是开源的,尤其学习源码特别有帮助,下载各种软件和工具也是十分方便,多尝试去阅读英文,对自己有好处,也是你区别于一般程序员的一种体现。 学习完以上知识后,一定要找几个综合一点的案例实操,从头到尾,从前端到后台撸一遍,了解真实的企业开发流程和常用工具,这个十分重要,虽然不能够与真实环境相比,起码越接近越好撒,给网上比较好的综合案例吧,然后有了这些经验,就可以去找实习了,过程比较虐心哈,你们自己去体会。 秋招的时候,有实习经历肯定会加分的,但是没有实习的也有机会的,面试问的最多的还是基础,基础,基础,重要的事情说三遍,特别是计算机基础和Java基础,常用框架基本是问底层原理。 在学习java的过程当中有遇见任何问题,可以加入我的Java交流学习秋秋qun:374320282,多多交流问题,互帮互助,群里有不错的学习教程和开发工具。学习java有任何问题(学习方法,学习效率,如何就业),可以随时来咨询我 杂谈作为一个转行人员,与科班出身的不一样,从头到尾我们必须要清楚自己的目标,每一步该干什么,大概花多长时间,遇到困难也要自己解决,经常就是一个小问题一卡就半天或者一天过去了,但是这些坑都要自己一个一个去踩,才会有所进步,才能有所成长。 报班与否:我自己当初也是面临这个选择。每个人的情况不一样,学习效率、时间块、财力、学习资源等等因素。报班好处:系统学习,整个计划不需要自己考虑,困难小,时间稍短,资源多;坏处:压力大,节奏快,花钱,自己思考的时间少。当然自学的话,面临的困难更多,但是解决问题的能力也是因人而异的,你需要有一颗强大的心脏。 准备时间早晚否:送分题,肯定是越早越好。但是实际上由于视野受限,一般大多数人不会很早准备 笨鸟先飞,但是如果没有方向,最后也会不知所踪。一定要对自己有个规划,然后一步一步的学习,只要下定决心要学,无论哪种方式,坚持、积极终会有所回报的。

优秀的个人博客,低调大师

Python零基础学习笔记(三十三)—— 窗体的控制

这里需要安装和下载pywin32导入相应的库 同时需要下载spy++工具来获取窗口句柄和标题 打开qq执行代码就有效果了 控制窗体的显示和隐藏 ''' import time import win32con import win32gui ''' #找出窗体的编号 QQWin = win32gui.FindWindow("Tedkaafa","QQ") #窗口句柄和标题 #隐藏窗体 win32gui.ShowWindow(QQWin,win32con.SW_HIDE) #显示窗体 win32gui.ShowWindow(QQWin,win32con.SW_SHOW) ''' while True: QQWin = win32gui.FindWindow("TXGuiFoundation", "QQ") win32gui.ShowWindow(QQWin, win32con.SW_HIDE) time.sleep(2) win32gui.ShowWindow(QQWin, win32con.SW_SHOW) time.sleep(2) ''' 控制窗体的位置和大小 ''' import win32con import win32gui import time import random QQWin = win32gui.FindWindow("TXGuiFoundation", "QQ") #参数1:控制的窗体 #参数2:大致方位,HWND_TOPMOST上方 #参数3:位置x #参数4:位置y #参数5:长度 #参数6:宽度 while True: time.sleep(0.2) x = random.randrange(600) y = random.randrange(800) win32gui.SetWindowPos(QQWin, win32con.HWND_TOPMOST, x, y, 600, 600, win32con.SWP_SHOWWINDOW)

优秀的个人博客,低调大师

Python零基础学习笔记(三十七)—— 栈和队列

#模拟栈结构 stack = [] #压栈(向栈里面存数据) stack.append("A") print(stack) stack.append("B") stack.append("C") print(stack) #出栈(在栈里面取数据) res1 = stack.pop() print(res1) print(stack) res2 = stack.pop() print(res2) print(stack) res3 = stack.pop() print(res3) print(stack) #模拟队列 import collections #创建队列 queue = collections.deque() print(queue) #进队 queue.append("A") print(queue) queue.append("B") print(queue) #出队 res1 = queue.popleft() print(res1) print(queue) res2 = queue.popleft() print(res2) print(queue)

优秀的个人博客,低调大师

Python零基础学习笔记(二十五)—— 装饰器

''' 概念:是一个闭包,把一个函数当作参数返回一个替代版的函数 本质上是一个返回函数的函数 ''' #简单的装饰器 def func1(): print("My name is jjking.") def func2(): print("******************") func1() func2() def func3(func): def inner(): print("******************") func() return inner #f是func1的加强版本 f = func3(func1) f() def outer(func): def inner(age): if age < 0: age = 0 func(age) return inner #使用@符号将装饰器应用到函数 #python2.4支持使用@符号 @outer def say(age): print("My age is %d"% (age)) #say = outer(say) say(-12) def outer(func): def inner(*args, **kwargs): #添加修改的功能 print("&&&&&&&&") func(*args, **kwargs) return inner @outer def say(name, age): print("My name is %s, I am %d years old."%(name, age)) say("jjking", 23)

优秀的个人博客,低调大师

Python零基础学习笔记(二十九)—— OS模块

import os ''' OS:包含了普遍的操作系统的功能 ''' #获取操作系统类型 nt->Windows posix->Linux/Unix或Mac OS X print(os.name) #打印操作系统详细信息,注意:windows 不支持 #print(os.uname()) #获取操作系统的环境变量 print(os.environ) #获取指定环境变量 print(os.environ.get("ALLUSERSPROFILE")) #获取当前目录 print(os.curdir) #获取当前工作目录,即当前脚本所在的目录 print(os.getcwd()) #返回指定目录下的所有文件(列表形式) print(os.listdir(r"C:\Users\Administrator\PycharmProjects\untitled\day006")) #在当前目录下创建新目录 #os.mkdir("My name") #删除目录 #os.rmdir("My name") #获取文件属性 print(os.stat("断言.py")) #重命名 #os.rename("My name","sd") #删除普通文件 #os.remove("sd") #运行shell命令 #os.system("notepad") #os.system("write") #os.system("shutdown -s -t 500") #自动关机 #os.system("taskkill /f /im notepad.exe") #关闭notepad进程 ''' os.path ''' #查看当前的绝对路径 print(os.path.abspath("./sd")) #拼接路径 p1 = r"C:\Users\Administrator\PycharmProjects\untitled\day011" p2 = "jjking"#注意:开始不能有斜杠 print(os.path.join(p1,p2)) #拆分路径 path2 = r"C:\Users\Administrator\PycharmProjects\untitled\day011\sd" print(os.path.split(path2)) #获取扩展名 print(os.path.splitext(path2)) #是否是目录 print(os.path.isdir(path2)) #判断文件是否存在 path3 = r"C:\Users\Administrator\PycharmProjects\untitled\day011\断言.py" print(os.path.isfile(path3)) #判断文件是否存在 print(os.path.exists(path3)) #获得文件字节 print(os.path.getsize(path3)) #获得文件路径 print(os.path.dirname(path3)) #获得文件名 print(os.path.basename(path3))

优秀的个人博客,低调大师

Python零基础学习笔记(二十三)—— 迭代器

from collections import Iterable, Iterator ''' 可迭代对象:可以直接作用于for循环的对象统称为可迭代对象 (Iterable) 可以用isinstance()去判断一个对象是否是Iterable对象 可以直接作用于for的数据类型一般分两种 1、集合类数据类型:list、 tuple、 dict、 set、 string 2、是generator,包括生成器和带yield的generator function ''' print(isinstance([],Iterable)) print(isinstance((),Iterable)) print(isinstance({},Iterable)) print(isinstance("",Iterable)) print(isinstance((x for x in range(10)),Iterable)) print(isinstance(1,Iterable)) ''' 迭代器:不但可以作用于for循环,还可以被next()函数不断的调用并返回下一个值 直到最后抛出一个StopIteration错误表示无法继续返回下一个值 可以被next()函数调用并不断返回下一个之的对象称为迭代器 (Iterator对象) 可以用isinstance()函数判断一个对象是否是可迭代对象 ''' print(isinstance([],Iterator)) print(isinstance((),Iterator)) print(isinstance({},Iterator)) print(isinstance("",Iterator)) print(isinstance((x for x in range(10)),Iterator)) l = (x for x in range(4)) print(l) print(next(l)) print(next(l)) print(next(l)) print(next(l)) lq = (x for x in [1, 2, 3, 5]) print(next(lq)) print(next(lq)) print(next(lq)) print(next(lq)) #同理tuple、dict、set、string都可以 #转换成Iterator对象 a = iter([2, 4, 6]) print(next(a)) print(next(a)) print(next(a)) print(isinstance((a), Iterator)) endstr = "end" str = "" for line in iter(input, endstr): str += line + "\n" print(str)

优秀的个人博客,低调大师

Python零基础学习笔记(二十一)—— dict字典

''' 概述: 使用键-值(key-value)存储,具有极快的查找速度 key的特性: 1、字典中的key必须唯一,一个字典可以存储多个键值对 2、key必须是不可变的对象 3、字符串、整数等都是不可变的,可以作为key 4、list是可变的,不能作为key ''' ''' 保存多位学生成绩 使用字典,学号为key,学生成绩作为值 ''' dict1 = {"1101":60, "1102":80} print(dict1) #元素的访问 #获取: 字典名[key] print(dict1["1102"]) print(dict1.get("1103")) ret = dict1.get("1103") if ret ==None: print("不存在!") else: print("存在!") #添加 dict1["1103"] = 90 #因为一个key对应一个value,所以,多次对一个key的value赋值,其实就是修改值 dict1["1101"] = 70 print(dict1) #删除 dict1.pop("1102") print(dict1) #遍历 for key in dict1: print(key) print(dict1.values()) for value in dict1.values(): print(value) print(dict1.items()) for k, v in dict1.items(): print(k, v) print(enumerate(dict1)) for i, c in enumerate(dict1): #枚举法 print(i,c) ''' #和list比较 1、查找和插入的速度极快,不会随着key-value的增加而变慢 2、需要占大量的内存,内存浪费多 ''' ''' list: 缺点: 查找和插入的速度随着数据量的增多而减慢 优点: 内存占用小,节省内存 '''

优秀的个人博客,低调大师

Python零基础学习笔记(十六)—— if-elif-else语句

''' if-elif-else语句 格式: if 表达式1: 语句1 elif 表达式2: 语句2 elif 表达式3: 语句3 ...... elif 表达式4: 语句4 else: #可有可无 语句n 逻辑:当程序执行到if-elif-else语句时,首先计算【表达式1】的值, 如果【表达式1】的值为真,则执行【语句1】,执行结束 跳过整个if-elif-else语句 如果【表达式1】的值为假,那么计算【表达式2】的值, 如果【表达式2】的值为真,则执行【语句2】,执行结束 跳过整个if-elif-else语句 ...... 如果没有1个是真的且有else的情况下,执行else里面的语句 否则直接继续向下执行,此段程序相当于没有执行 ''' #判断年龄 执行效率:每条语句必须执行一次,平局时间复杂度相当于5 age = int(input()) if age <= 0: print("没出生呢!") if age > 0 and age <= 3: print("婴儿") if age > 3 and age <= 7: print("幼儿") if age >7 and age <= 18: print("未成年") else: print("成年了") #优化方法 和上一个相比较执行效率提高,平均执行次数2.5 age = int(input()) if age <= 0: print("没出生呢!") elif age > 0 and age <= 3: print("婴儿") elif age > 3 and age <= 7: print("幼儿") elif age >7 and age <= 18: print("未成年") else: print("成年了") #逻辑优化 当执行 age<=3 的时候,一定是 age>0, 以此类推 age = int(input()) if age <= 0: print("没出生呢!") elif age <= 3: print("婴儿") elif age <= 7: print("幼儿") elif age <= 18: print("未成年") else: print("成年了") ''' 这个语句可以用来写只能回答,像小艾同学,天猫精灵啊。。。。 可以用提取关键字的方法来回答问题 在c#里曾经写过那个唐诗三百首,当你输入唐诗的诗名或作者显示相应的古诗词 '''

优秀的个人博客,低调大师

Python零基础学习代码实践 —— 99乘法表

学了for循环语句之后,就会变得相当简单了 #99乘法表 for a in range(10): for b in range(10): if a!=0 and b!=0: print(a,"*", b,"=", a * b) 执行结果: 1 * 1 = 1 1 * 2 = 2 1 * 3 = 3 1 * 4 = 4 1 * 5 = 5 1 * 6 = 6 1 * 7 = 7 1 * 8 = 8 1 * 9 = 9 2 * 1 = 2 2 * 2 = 4 2 * 3 = 6 2 * 4 = 8 2 * 5 = 10 2 * 6 = 12 2 * 7 = 14 2 * 8 = 16 2 * 9 = 18 3 * 1 = 3 3 * 2 = 6 3 * 3 = 9 3 * 4 = 12 3 * 5 = 15 3 * 6 = 18 3 * 7 = 21 3 * 8 = 24 3 * 9 = 27 4 * 1 = 4 4 * 2 = 8 4 * 3 = 12 4 * 4 = 16 4 * 5 = 20 4 * 6 = 24 4 * 7 = 28 4 * 8 = 32 4 * 9 = 36 5 * 1 = 5 5 * 2 = 10 5 * 3 = 15 5 * 4 = 20 5 * 5 = 25 5 * 6 = 30 5 * 7 = 35 5 * 8 = 40 5 * 9 = 45 6 * 1 = 6 6 * 2 = 12 6 * 3 = 18 6 * 4 = 24 6 * 5 = 30 6 * 6 = 36 6 * 7 = 42 6 * 8 = 48 6 * 9 = 54 7 * 1 = 7 7 * 2 = 14 7 * 3 = 21 7 * 4 = 28 7 * 5 = 35 7 * 6 = 42 7 * 7 = 49 7 * 8 = 56 7 * 9 = 63 8 * 1 = 8 8 * 2 = 16 8 * 3 = 24 8 * 4 = 32 8 * 5 = 40 8 * 6 = 48 8 * 7 = 56 8 * 8 = 64 8 * 9 = 72 9 * 1 = 9 9 * 2 = 18 9 * 3 = 27 9 * 4 = 36 9 * 5 = 45 9 * 6 = 54 9 * 7 = 63 9 * 8 = 72 9 * 9 = 81

资源下载

更多资源
Mario

Mario

马里奥是站在游戏界顶峰的超人气多面角色。马里奥靠吃蘑菇成长,特征是大鼻子、头戴帽子、身穿背带裤,还留着胡子。与他的双胞胎兄弟路易基一起,长年担任任天堂的招牌角色。

Spring

Spring

Spring框架(Spring Framework)是由Rod Johnson于2002年提出的开源Java企业级应用框架,旨在通过使用JavaBean替代传统EJB实现方式降低企业级编程开发的复杂性。该框架基于简单性、可测试性和松耦合性设计理念,提供核心容器、应用上下文、数据访问集成等模块,支持整合Hibernate、Struts等第三方框架,其适用范围不仅限于服务器端开发,绝大多数Java应用均可从中受益。

Sublime Text

Sublime Text

Sublime Text具有漂亮的用户界面和强大的功能,例如代码缩略图,Python的插件,代码段等。还可自定义键绑定,菜单和工具栏。Sublime Text 的主要功能包括:拼写检查,书签,完整的 Python API , Goto 功能,即时项目切换,多选择,多窗口等等。Sublime Text 是一个跨平台的编辑器,同时支持Windows、Linux、Mac OS X等操作系统。

WebStorm

WebStorm

WebStorm 是jetbrains公司旗下一款JavaScript 开发工具。目前已经被广大中国JS开发者誉为“Web前端开发神器”、“最强大的HTML5编辑器”、“最智能的JavaScript IDE”等。与IntelliJ IDEA同源,继承了IntelliJ IDEA强大的JS部分的功能。

用户登录
用户注册