面试之 Python 进阶
前端相關
1.談談你對http協議的認識。
瀏覽器本質,socket客戶端遵循Http協議
HTTP協議本質:通過\r\n分割的規范+ 請求響應之后斷開鏈接 == > 無狀態、 短連接
具體:
Http協議是建立在tcp之上的,是一種規范,它規范定了發送的數據的數據格式,然而這個數據格式是通過\r\n 進行分割的,請求頭與請求體也是通過2個\r\n分割的,響應的時候,響應頭與響應體也是通過\r\n分割,并且還規定已請求已響應就會斷開鏈接,即---> 短連接、無狀態
2.談談你對websocket協議的認識。
a.什么是websocket?
是給瀏覽器新建的一套協議
協議規定:創建連接后不斷開
通過'\r\n'分割,讓客戶端和服務端創建連接后不斷開、驗證+數據加密
# b.本質:
# 就是一個創建連接后不斷開的socket
# 當連接成功后:
- 客戶端(瀏覽器)會自動向服務端發送消息
- 服務端接收后,會對該數據加密:base64(sha1(swk+magic_string))
- 構造響應頭
- 發送給客戶端
# 建立雙工通道,進行收發數據
# c.框架中是如何使用websocket的?
django:channel
flask:gevent-websocket
tornado:內置
# d.websocket的優缺點
優點:代碼簡單,不再重復創建連接
缺點:兼容性沒有長輪詢好,如IE會有不兼容
?WebSocket和HTTP的區別:
? http協議是用在應用層的協議,他是基于tcp協議的,http協議建立鏈接也必須要有三次握手才能發送信息。
? http鏈接分為短鏈接,長鏈接,短鏈接是每次請求都要三次握手才能發送自己的信息。即每一個request對應一個response。長鏈接是在一定的期限內保持鏈接。保持TCP連接不斷開。客戶端與服務器通信,必須要有客戶端發起然后服務器返回結果。客戶端是主動的,服務器是被動的。?
? WebSocket他是為了解決客戶端發起多個http請求到服務器資源瀏覽器必須要經過長時間的輪訓問題而生的,他實現了多路復用,他是全雙工通信。在webSocket協議下客服端和瀏覽器可以同時發送信息。
? 建立了WenSocket之后服務器不必在瀏覽器發送request請求之后才能發送信息到瀏覽器。這時的服務器已有主動權想什么時候發就可以發送信息到服務器。而且信息當中不必在帶有head的部分信息了與http的長鏈接通信來說,這種方式,不僅能降低服務器的壓力。而且信息當中也減少了部分多余的信息。
3.什么是magic string ?
客戶端向服務端發送消息時,會有一個'sec-websocket-key'和'magic string'的隨機字符串(魔法字符串)
服務端接收到消息后會把他們連接成一個新的key串,進行編碼、加密,確保信息的安全性
4.如何創建響應式布局?
# a.可以通過引用Bootstrap實現 # b.通過看Bootstrap源碼文件,可知其本質就是通過CSS實現的<style>/*瀏覽器窗口寬度大于768,背景色變為 green*/@media (min-width: 768px) {.pg-header{background-color: green;}}/*瀏覽器窗口寬度大于992,背景色變為 pink*/@media (min-width: 992px) {.pg-header{background-color: pink;}}</style> </head> <body> <div class="pg-header"></div> </body>5.你曾經使用過哪些前端框架?
jQuery
- BootStrap,H-ui
- Vue.js(與vue齊名的前端框架React和Angular)
6.什么是ajax請求?并使用jQuery和XMLHttpRequest對象實現一個ajax請求。
1.沒用ajax:瀏覽器訪問服務器請求,用戶看得到(頁面刷新也就等同于重新發請求,刷新看得到,也就等同于請求看得到)。等請求完,頁面刷新,新內容出現,用戶看到新內容。
2.用ajax:瀏覽器訪問服務器請求,用戶看不到,是悄悄進行。等請求完,頁面不刷新,新內容也會出現,用戶看到新內容。
http://www.cnblogs.com/wupeiqi/articles/5703697.html
7.如何在前端實現輪訓?
# 輪詢是在特定的的時間間隔(如每1秒),由瀏覽器對服務器發出HTTP request, # 然后由服務器返回最新的數據給客戶端的瀏覽器。 var xhr = new XMLHttpRequest();setInterval(function(){xhr.open('GET','/user');xhr.onreadystatechange = function(){};xhr.send();},1000)8.如何在前端實現長輪訓?
# ajax實現:在發送ajax后,服務器端會阻塞請求直到有數據傳遞或超時才返回。 # 客戶端JavaScript響應處理函數會在處理完服務器返回的信息后,再次發出請求,重新建立連接。function ajax(){var xhr = new XMLHttpRequest();xhr.open('GET','/user');xhr.onreadystatechange = function(){ajax();};xhr.send();}9.vuex的作用?
1.不同組件之間共享狀態,可以進行狀態的修改和讀取。
2.可以理解為是一個全局對象,所有頁面都可以訪問
3.還有比較重要的單一狀態樹管理,讓數據的修改脈絡更加清晰,便于定位問題。
# 比如用戶做了一些加減的操作、三個頁面都要用、可以用傳參、但是很麻煩、這種時候用vuex就簡單一些
10.vue中的路由的攔截器的作用?
# 統一處理所有http請求和響應時,可以用axios的攔截器。
# 通過配置http response inteceptor,當后端接口返回401 Unauthorized(未授權),讓用戶重新登錄。
# so可以用來做登錄攔截驗證
11.axios的作用?
# axios是vue-resource后出現的Vue請求數據的插件
# 可以做的事情:
從瀏覽器中創建 XMLHttpRequest
從 node.js 發出 http 請求
支持 Promise API
攔截請求和響應
轉換請求和響應數據
取消請求
自動轉換JSON數據
客戶端支持防止 CSRF/XSRF
12.列舉vue的常見指令。
# 1、v-if指令:判斷指令,根據表達式值得真假來插入或刪除相應的值。
# 2、v-show指令:
? # 條件渲染指令,無論返回的布爾值是true還是false,元素都會存在html中,
? # false的元素會隱藏在html中,并不會刪除.
# 3、v-else指令:配合v-if或v-else使用。
# 4、v-for指令:循環指令,相當于遍歷。
# 5、v-bind:給DOM綁定元素屬性。
# 6、v-on指令:監聽DOM事件。
13.簡述jsonp及實現原理?
應為有同源策略,所以需要使用scripy 標簽
# 原理:
1、先在客戶端注冊一個callback, 然后把callback的名字傳給服務器。
2、此時,服務器先生成 json 數據。
3、然后以 javascript 語法的方式,生成一個function , function 名字就是傳遞上來的參數 jsonp.
4、最后將 json 數據直接以入參的方式,放置到 function 中,這樣就生成了一段 js 語法的文檔,返回給客戶端。
客戶端瀏覽器,解析script標簽,并執行返回的 javascript 文檔,此時數據作為參數,
傳入到了客戶端預先定義好的 callback 函數里.(動態執行回調函數)
# 注意
# JSON 是一種數據格式
# JSONP 是一種數據調用的方式
14.什么是cors ?
# 跨域資源共享(Cross-Origin Resource Sharing)
# 其本質是設置響應頭,使得瀏覽器允許跨域請求。
# 簡單請求(一次請求)
1、請求方式:HEAD、GET、POST
2、請求頭信息:
? ? Accept
? ? Accept-Language
? ? Content-Language
? ? Last-Event-ID
? ? Content-Type 對應的值是以下三個中的任意一個
? ? ? ? ? ? ? ? ? ? ? ? ? ? application/x-www-form-urlencoded
? ? ? ? ? ? ? ? ? ? ? ? ? ? multipart/form-data
? ? ? ? ? ? ? ? ? ? ? ? ? ? text/plain
# 非簡單請求(兩次請求)
在發送真正的請求之前,會默認發送一個'options'請求,做'預檢',預檢成功后才發送真正的請求
? ? # 預檢:
? ? 如果復雜請求是PUT等請求,則服務端需要設置允許某請求,否則“預檢”不通過
? ? ? ? Access-Control-Request-Method
? ? 如果復雜請求設置了請求頭,則服務端需要設置允許某請求頭,否則“預檢”不通過
? ? ? ? Access-Control-Request-Headers
15.列舉Http請求中常見的請求方式?
http請求方法有8種:
? ? ? ? 'GET'
? ? ? ? 'POST'
? ? ? ? 'HEAD'
? ? ? ? 'OPTIONS'
? ? ? ? 'PUT'(修改數據)
? ? ? ? 'DELETE'
? ? ? ? 'TRACE'
? ? ? ? 'CONNECT'
16.列舉Http請求中的狀態碼?
# 2開頭(成功)
? ? 200:請求成功
? ? 202:已接受請求,尚未處理
? ? 204:請求成功,且不需返回內容
# 3開頭(重定向)
? ? 301:永久重定向
? ? 302:臨時重定向
# 4開頭(客戶端錯誤)
? ? 400(Bad Request):請求的語義或是參數有錯
? ? 403(Forbidden):服務器拒絕了請求(csrf)
? ? 404(Not Found):找不到頁面(資源)
# 5開頭(服務器錯誤)
? ? 500:服務器遇到錯誤,無法完成請求
? ? 502:網關錯誤,一般是服務器壓力過大導致連接超時 ? ? ??
? ? 503:服務器宕機
17.列舉Http請求中常見的請求頭?
# 常見請求頭:User-Agent、Referer、Host、Cookie、Connection、Accept
18.看圖寫結果(js):
李杰
Python框架
19.django、flask、tornado框架的比較?
- django,大而全的框架它的內部組件比較多,內部提供:ORM、Admin、中間件、Form、ModelForm、Session、緩存、信號、CSRF;功能也都挺完善的
- flask,微型框架,內部組件就比較少了,但是有很多第三方組件來擴展它,比如說有那個wtform(與django的modelform類似,表單驗證)、flask-sqlalchemy(操作數據庫的)、flask-session、flask-migrate、flask-script、blinker可擴展強,第三方組件豐富。所以對他本身來說有那種短小精悍的感覺
- tornado,異步非阻塞。是一個輕量級的Web框架,異步非阻塞+內置WebSocket功能。'目標':通過一個線程處理N個并發請求(處理IO)。'內部組件:內部自己實現socket、路由系統、視圖、模板、cookie、csrf
django和flask的共同點就是,他們2個框架都沒有寫socket,所以他們都是利用第三方模塊wsgi。
但是內部使用的wsgi也是有些不同的:django本身運行起來使用wsgiref,而flask使用werkzeug wsgi
還有一個區別就是他們的請求管理不太一樣:django是通過將請求封裝成request對象,再通過參數傳遞,而flask是通過上下文管理機制
20.什么是wsgi?
是web服務網關接口,是一套協議。
是通過以下模塊實現了wsgi協議:
? ? - wsgiref
? ? - werkzurg
? ? - uwsgi ? 關于部署
以上模塊本質:編寫socket服務端,用于監聽請求,當有請求到來,則將請求數據進行封裝,然后交給web框架處理。
Django?
21.django請求的生命周期?
用戶請求進來先走到 wsgi --> 然后將請求交給 jango的中間件 --> 穿過django中間件(方法是process_request)接著就是 路由匹配 --> 路由匹配成功之后就執行相應的 視圖函數 --> 在視圖函數中可以調用orm做數據庫操作?--> 再從模板路徑 將模板拿到 --> 然后在后臺進行模板渲染 --> 模板渲染完成之后就變成一個字符串 --> 再把這個字符串經過所有中間件(方法:process_response) 和wsgi 返回給用戶
22.列舉django的內置組件?
form 組件 - 對用戶請求的數據進行校驗 - 生成HTML標簽 PS: - form對象是一個可迭代對象。 - 問題:choice的數據如果從數據庫獲取可能會造成數據無法實時更新- 重寫構造方法,在構造方法中重新去數據庫獲取值。- ModelChoiceField字段from django.forms import Formfrom django.forms import fieldsfrom django.forms.models import ModelChoiceFieldclass UserForm(Form):name = fields.CharField(label='用戶名',max_length=32)email = fields.EmailField(label='郵箱')ut_id = ModelChoiceField(queryset=models.UserType.objects.all()) 依賴:class UserType(models.Model):title = models.CharField(max_length=32)def __str__(self):return self.title信號 django的信號其實就是django內部為開發者預留的一些自定制功能的鉤子。 只要在某個信號中注冊了函數,那么django內部執行的過程中就會自動觸發注冊在信號中的函數。 如: pre_init # django的modal執行其構造方法前,自動觸發 post_init # django的modal執行其構造方法后,自動觸發 pre_save # django的modal對象保存前,自動觸發 post_save # django的modal對象保存后,自動觸發 場景: 在數據庫某些表中添加數據時,可以進行日志記錄。CSRF 目標:防止用戶直接向服務端發起POST請求。 對所有的post請求做驗證/ 將jango生成的一串字符串發送給我們,一種是從請求體發過來,一種是放在隱藏的標簽里面用的是process_view 方案:先發送GET請求時,將token保存到:cookie、Form表單中(隱藏的input標簽), 以后再發送請求時只要攜帶過來即可。ContentType contenttype是django的一個組件(app), 為我們找到django程序中所有app中的所有表并添加到記錄中。可以使用他再加上表中的兩個字段實現:一張表和N張表創建FK關系。 - 字段:表名稱 - 字段:數據行ID 應用:路飛表結構優惠券和專題課和學位課關聯。中間件 對所有的請求進行批量處理,在視圖函數執行前后進行自定義操作。 應用:用戶登錄校驗 問題:為甚么不使用裝飾器? 如果不使用中間件,就需要給每個視圖函數添加裝飾器,太繁瑣session cookie與session區別 (a)cookie是保存在瀏覽器端的鍵值對,而session是保存的服務器端的鍵值對,但是依賴cookie。(也可以不依賴cookie,可以放在url,或請求頭但是cookie比較方便) (b)以登錄為例,cookie為通過登錄成功后,設置明文的鍵值對,并將鍵值對發送客戶端存,明文信息可能存在泄漏,不安全;session則是生成隨機字符串,發給用戶,并寫到瀏覽器的cookie中,同時服務器自己也會保存一份。 (c)在登錄驗證時,cookie:根據瀏覽器發送請求時附帶的cookie的鍵值對進行判斷,如果存在,則驗證通過;session:在請求用戶的cookie中獲取隨機字符串,根據隨機字符串在session中獲取其對應的值進行驗證cors跨域(場景:前后端分離時,本地測試開發時使用) 如果網站之間存在跨域,域名不同,端口不同會導致出現跨域,但凡出現跨域,瀏覽器就會出現同源策略的限制 解決:在我們的服務端給我們響應數據,加上響應頭---> 在中間件加的緩存 常用的數據放在緩存里面,就不用走視圖函數,請求進來通過所有的process_request,會到緩存里面查數據,有就直接拿,沒有就走視圖函數關鍵點:1:執行完所有的process_request才去緩存取數據2:執行完所有的process_response才將數據放到緩存關于緩存問題 1:為什么放在最后一個process_request才去緩存 因為需要驗證完用戶的請求,才能返回數據2:什么時候將數據放到緩存中 第一次走中間件,緩存沒有數據,會走視圖函數,取數據庫里面取數據, 當走完process_response,才將數據放到緩存里,因為,走process_response的時候可能給我們的響應加處理3.為什么使用緩存 將常用且不太頻繁修改的數據放入緩存。 以后用戶再來訪問,先去緩存查看是否存在,如果有就返回 否則,去數據庫中獲取并返回給用戶(再加入到緩存,以便下次訪問)23.列舉django中間件的5個方法?以及django中間件的應用場景?
process_request(self,request) ?先走request 通過路由匹配返回
process_view(self, request, callback, callback_args, callback_kwargs) 再返回執行view
process_template_response(self,request,response) ? 當視圖函數的返回值
process_exception(self, request, exception) ?當視圖函數的返回值對象中有render方法時,該方法才會被調用
process_response(self, request, response)
24.簡述什么是FBV和CBV?
FBV 基于函數 # FBV 寫法 # urls.pyurl(r'^login/$',views.login, name="login"),# views.py def login(request):if request.method == "POST":print(request.POST)return render(request,"login.html")# HTML <!DOCTYPE html> <html lang="en"> <head><meta charset="UTF-8"><meta http-equiv="X-UA-Compatible" content="IE=edge"><meta name="viewport" content="width=device-width, initial-scale=1"><title>登錄頁面</title> </head> <body> <form action="{% url 'login' %}" method="post" enctype="multipart/form-data"><input type="text" name="user2"><input type="file" name="file"><input type="submit" value="提交"></form> </body> </html>CBV 基于類 # urls.py url(r'^login/$',views.Login.as_view(), name="login"), # views.py from django.views import View class Login(View): # 類首字母大寫def get(self,request):return render(request,"login.html")def post(self,request):print(request.POST)return HttpResponse("OK")加裝飾器================================= class IndexView(View):# 如果是crsf相關,必須放在此處def dispach(self,request):# 通過反射執行post/get @method_decoretor(裝飾器函數)def get(self,request):passdef post(self,request):pass 路由:IndexView.as_view()25.FBV與CBV的區別
- 沒什么區別,因為他們的本質都是函數。CBV的.as_view()返回的view函數,view函數中調用類的dispatch方法, 在dispatch方法中通過反射執行get/post/delete/put等方法。D非要說區別的話: - CBV比較簡潔,GET/POST等業務功能分別放在不同get/post函數中。FBV自己做判斷進行區分。26.django的request對象是在什么時候創建的?
當請求一個頁面時, Django會建立一個包含請求元數據的 HttpRequest 對象. 當Django 加載對應的視圖時, HttpRequest對象將作為視圖函數的第一個參數. 每個視圖會返回一個HttpResponse對象.27.如何給CBV的程序添加裝飾器?
添加裝飾器 方式一: from django.views import View from django.utils.decorators import method_decorator ---> 需要引入memethod_decoratordef auth(func):def inner(*args,**kwargs):return func(*args,**kwargs)return innerclass UserView(View):@method_decorator(auth)def get(self,request,*args,**kwargs):return HttpResponse('...') 方式二: - csrf的裝飾器要加到dispath前面 from django.views import View from django.utils.decorators import method_decorator from django.views.decorators.csrf import csrf_exempt,csrf_protect ---> 需要引入 csrf_exemptclass UserView(View):@method_decorator(csrf_exempt)def dispatch(self, request, *args, **kwargs):return HttpResponse('...')或者: from django.views import View from django.utils.decorators import method_decorator from django.views.decorators.csrf import csrf_exempt,csrf_protect@method_decorator(csrf_exempt,name='dispatch') ---> 指定名字 class UserView(View):def dispatch(self, request, *args, **kwargs):return HttpResponse('...')28.列舉django orm 中所有的方法(QuerySet對象的所有方法)
返回QuerySet對象的方法有:all()filter()exclude()order_by()reverse()distinct()特殊的QuerySet:values() 返回一個可迭代的字典序列values_list() 返回一個可迭代的元組序列返回具體對象的:get()first()last()返回布爾值的方法有:exists()返回數字的方法有:count()?29.only和defer的區別?
def defer(self, *fields):models.UserInfo.objects.defer('username','id')或models.UserInfo.objects.filter(...).defer('username','id')#映射中排除某列數據def only(self, *fields):#僅取某個表中的數據models.UserInfo.objects.only('username','id')或models.UserInfo.objects.filter(...).only('username','id')30.select_related和prefetch_related的區別?
# 他倆都用于連表查詢,減少SQL查詢次數 select_related主要針一對一和多對一關系進行優化,通過多表join關聯查詢,一次性獲得所有數據, 存放在內存中,但如果關聯的表太多,會嚴重影響數據庫性能。 def index(request):obj = Book.objects.all().select_related("publisher")return render(request, "index.html", locals())prefetch_related是通過分表,先獲取各個表的數據,存放在內存中,然后通過Python處理他們之間的關聯。 def index(request):obj = Book.objects.all().prefetch_related("publisher")return render(request, "index.html", locals())# 舉例 def select_related(self, *fields)# 性能相關:表之間進行join連表操作,一次性獲取關聯的數據。model.tb.objects.all().select_related()model.tb.objects.all().select_related('外鍵字段')model.tb.objects.all().select_related('外鍵字段__外鍵字段')def prefetch_related(self, *lookups)# 性能相關:多表連表操作時速度會慢,使用其執行多次SQL查詢在Python代碼中實現連表操作。# 獲取所有用戶表# 獲取用戶類型表where id in (用戶表中的查到的所有用戶ID)models.UserInfo.objects.prefetch_related('外鍵字段')from django.db.models import Count, Case, When, IntegerFieldArticle.objects.annotate(numviews=Count(Case(When(readership__what_time__lt=treshold, then=1), output_field=CharField(),)))students = Student.objects.all().annotate(num_excused_absences=models.Sum(models.Case(models.When(absence__type='Excused', then=1),default=0,output_field=models.IntegerField())))?
# 1次SQL # select * from userinfo objs = UserInfo.obejcts.all() for item in objs:print(item.name)# n+1次SQL # select * from userinfo objs = UserInfo.obejcts.all() for item in objs:# select * from usertype where id = item.id print(item.name,item.ut.title)# 1次SQL,使用select_related() # select * from userinfo inner join usertype on userinfo.ut_id = usertype.id objs = UserInfo.obejcts.all().select_related('ut') 連表查詢 for item in objs:print(item.name,item.ut.title).prefetch_related()# select * from userinfo where id <= 8# 計算:[1,2]# select * from usertype where id in [1,2]objs = UserInfo.obejcts.filter(id__lte=8).prefetch_related('ut')for obj in objs:print(obj.name,obj.ut.title)31.filter和exclude的區別?
def filter(self, *args, **kwargs)# 條件查詢(符合條件)# 查出符合條件# 條件可以是:參數,字典,Qdef exclude(self, *args, **kwargs)# 條件查詢(排除條件)# 排除不想要的# 條件可以是:參數,字典,Q32.列舉django orm中三種能寫sql語句的方法。
# 原生SQL ---> connection from django.db import connection, connections cursor = connection.cursor() # cursor = connections['default'].cursor() cursor.execute("""SELECT * from auth_user where id = %s""", [1]) row = cursor.fetchone() # fetchall()/fetchmany(..)# 靠近原生SQL-->extra\raw # extradef extra(self, select=None, where=None, params=None, tables=None, order_by=None, select_params=None)# 構造額外的查詢條件或者映射,如:子查詢Entry.objects.extra(select={'new_id': "select col from sometable where othercol > %s"},select_params=(1,))Entry.objects.extra(where=['headline=%s'], params=['Lennon'])Entry.objects.extra(where=["foo='a' OR bar = 'a'", "baz = 'a'"])Entry.objects.extra(select={'new_id': "select id from tb where id > %s"}, s elect_params=(1,), order_by=['-nid'])# raw def raw(self, raw_query, params=None, translations=None, using=None):# 執行原生SQLmodels.UserInfo.objects.raw('select * from userinfo')# 如果SQL是其他表時,必須將名字設置為當前UserInfo對象的主鍵列名models.UserInfo.objects.raw('select id as nid,name as title from 其他表')# 為原生SQL設置參數models.UserInfo.objects.raw('select id as nid from userinfo where nid>%s', params=[12,])# 將獲取的到列名轉換為指定列名name_map = {'first': 'first_name', 'last': 'last_name', 'bd': 'birth_date', 'pk': 'id'}Person.objects.raw('SELECT * FROM some_other_table', translations=name_map)# 指定數據庫models.UserInfo.objects.raw('select * from userinfo', using="default")33.django orm 中如何設置讀寫分離?
# 方式一:手動使用queryset的using方法 from django.shortcuts import render,HttpResponse from app01 import models def index(request):models.UserType.objects.using('db1').create(title='普通用戶')# 手動指定去某個數據庫取數據result = models.UserType.objects.all().using('db1')print(result)return HttpResponse('...')# 方式二:寫配置文件 class Router1:# 指定到某個數據庫取數據def db_for_read(self, model, **hints):"""Attempts to read auth models go to auth_db."""if model._meta.model_name == 'usertype':return 'db1'else:return 'default'# 指定到某個數據庫存數據def db_for_write(self, model, **hints):"""Attempts to write auth models go to auth_db."""return 'default' # 再寫到配置 DATABASES = {'default': {'ENGINE': 'django.db.backends.sqlite3','NAME': os.path.join(BASE_DIR, 'db.sqlite3'),},'db1': {'ENGINE': 'django.db.backends.sqlite3','NAME': os.path.join(BASE_DIR, 'db.sqlite3'),} } DATABASE_ROUTERS = ['db_router.Router1',]34.F和Q的作用?
# F:主要用來獲取原數據進行計算。 # Django 支持 F() 對象之間以及 F() 對象和常數之間的加減乘除和取模的操作。 # 修改操作也可以使用F函數,比如將每件商品的價格都在原價格的基礎上增加10 from django.db.models import F from app01.models import GoodsGoods.objects.update(price=F("price")+10) # 對于goods表中每件商品的價格都在原價格的基礎上增加10元F查詢專門對對象中某列值的操作,不可使用__雙下劃線! Q:用來進行復雜查詢Q查詢可以組合使用 “&”, “|” 操作符,當一個操作符是用于兩個Q的對象,它產生一個新的Q對象,Q對象可以用 “~” 操作符放在前面表示否定,也可允許否定與不否定形式的組合。Q對象可以與關鍵字參數查詢一起使用,不過一定要把Q對象放在關鍵字參數查詢的前面。Q(條件1) | Q(條件2) 或Q(條件1) & Q(條件2) 且Q(條件1) & ~Q(條件2) 非35.values和values_list的區別?
def values(self, *fields):# 獲取每行數據為字典格式def values_list(self, *fields, **kwargs):# 獲取每行數據為元祖36.如何使用django orm批量創建數據?
def bulk_create(self, objs, batch_size=None):# 批量插入# batch_size表示一次插入的個數objs = [models.DDD(name='r11'),models.DDD(name='r22')]models.DDD.objects.bulk_create(objs, 10)37.django的 Form?和 ModeForm 的作用?
- 作用:- 對用戶請求數據格式進行校驗- 自動生成HTML標簽- 區別:- Form,字段需要自己手寫。class Form(Form):xx = fields.CharField(.)xx = fields.CharField(.)xx = fields.CharField(.)xx = fields.CharField(.)- ModelForm,可以通過Meta進行定義class MForm(ModelForm):class Meta:fields = "__all__"model = UserInfo - 應用:只要是客戶端向服務端發送表單數據時,都可以進行使用,如:用戶登錄注冊38.django的Form組件中,如果字段中包含choices參數,請使用兩種方式實現數據源實時更新。
# 方式一:重寫構造方法,在構造方法中重新去數據庫獲取值class UserForm(Form):name = fields.CharField(label='用戶名',max_length=32)email = fields.EmailField(label='郵箱')ut_id = fields.ChoiceField(# choices=[(1,'普通用戶'),(2,'IP用戶')]choices=[])def __init__(self,*args,**kwargs):super(UserForm,self).__init__(*args,**kwargs)self.fields['ut_id'].choices = models.UserType.objects.all().values_list('id','title')# 方式二: ModelChoiceField字段from django.forms import Formfrom django.forms import fieldsfrom django.forms.models import ModelChoiceFieldclass UserForm(Form):name = fields.CharField(label='用戶名',max_length=32)email = fields.EmailField(label='郵箱')ut_id = ModelChoiceField(queryset=models.UserType.objects.all()) # 依賴:class UserType(models.Model):title = models.CharField(max_length=32)def __str__(self):return self.title39.django的Model中的ForeignKey字段中的on_delete參數有什么作用?
在django2.0后,定義外鍵和一對一關系的時候需要加on_delete選項,此參數為了避免兩個表里的數據不一致問題,不然會報錯: TypeError: __init__() missing 1 required positional argument: 'on_delete'舉例說明:user=models.OneToOneField(User) owner=models.ForeignKey(UserProfile)需要改成: user=models.OneToOneField(User,on_delete=models.CASCADE) --在老版本這個參數(models.CASCADE)是默認值 owner=models.ForeignKey(UserProfile,on_delete=models.CASCADE) --在老版本這個參數(models.CASCADE)是默認值參數說明: on_delete有CASCADE、PROTECT、SET_NULL、SET_DEFAULT、SET()五個可選擇的值 CASCADE:此值設置,是級聯刪除。 PROTECT:此值設置,是會報完整性錯誤。 SET_NULL:此值設置,會把外鍵設置為null,前提是允許為null。 SET_DEFAULT:此值設置,會把設置為外鍵的默認值。 SET():此值設置,會調用外面的值,可以是一個函數。 一般情況下使用CASCADE就可以了。40.django中csrf的實現機制?
目的:防止用戶直接向服務端發起POST請求- 用戶先發送GET獲取csrf token: Form表單中一個隱藏的標簽 + token - 發起POST請求時,需要攜帶之前發送給用戶的csrf token; - 在中間件的process_view方法中進行校驗。在html中添加{%csrf_token%}標簽41.django如何實現websocket?
django中可以通過channel實現websocket42.基于django使用ajax發送post請求時,都可以使用哪種方法攜帶csrf token?
# 方式一給每個ajax都加上上請求頭function Do1(){$.ajax({url:"/index/",data:{id:1},type:'POST',data:{csrfmiddlewaretoken:'{{ csrf_token }}',name:'alex'}success:function(data){console.log(data);}});}# 方式二:需要先下載jQuery-cookie,才能去cookie中獲取tokenfunction Do1(){$.ajax({url:"/index/",data:{id:1},type:'POST',headers:{'X-CSRFToken':$.cookie('csrftoken') // 去cookie中獲取},success:function(data){console.log(data);}});}方式三:搞個函數ajaxSetup,當有多的ajax請求,即會執行這個函數$.ajaxSetup({beforeSend:function (xhr,settings) {xhr.setRequestHeader("X-CSRFToken",$.cookie('csrftoken'))} });函數版本 <body> <input type="button" onclick="Do1();" value="Do it"/> <input type="button" onclick="Do2();" value="Do it"/> <input type="button" onclick="Do3();" value="Do it"/><script src="/static/jquery-3.3.1.min.js"></script> <script src="/static/jquery.cookie.js"></script> <script>$.ajaxSetup({beforeSend: function(xhr, settings) {xhr.setRequestHeader("X-CSRFToken", $.cookie('csrftoken'));}});function Do1(){$.ajax({url:"/index/",data:{id:1},type:'POST',success:function(data){console.log(data);}});}function Do2(){$.ajax({url:"/index/",data:{id:1},type:'POST',success:function(data){console.log(data);}});}function Do3(){$.ajax({url:"/index/",data:{id:1},type:'POST',success:function(data){console.log(data);}});} </script> </body>43.django中如何實現orm表中添加數據時創建一條日志記錄。
?給信號注冊函數
使用django的信號機制,可以在添加、刪除數據前后設置日志記錄
pre_init ?# Django中的model對象執行其構造方法前,自動觸發
post_init ?# Django中的model對象執行其構造方法后,自動觸發
pre_save ?# Django中的model對象保存前,自動觸發
post_save ?# Django中的model對象保存后,自動觸發
pre_delete ?# Django中的model對象刪除前,自動觸發
post_delete ?# Django中的model對象刪除后,自動觸發
44.django緩存如何設置?
jango中提供了6種緩存方式:開發調試(不加緩存)內存文件數據庫Memcache緩存(python-memcached模塊)Memcache緩存(pylibmc模塊)安裝第三方組件支持redis:django-redis組件設置緩存 # 全站緩存(中間件) MIDDLEWARE_CLASSES = (‘django.middleware.cache.UpdateCacheMiddleware’, #第一'django.middleware.common.CommonMiddleware',‘django.middleware.cache.FetchFromCacheMiddleware’, #最后 )# 視圖緩存 from django.views.decorators.cache import cache_page import time@cache_page(15) #超時時間為15秒 def index(request):t=time.time() #獲取當前時間return render(request,"index.html",locals())# 模板緩存 {% load cache %}<h3 style="color: green">不緩存:-----{{ t }}</h3>{% cache 2 'name' %} # 存的key<h3>緩存:-----:{{ t }}</h3> {% endcache %}45.django的緩存能使用redis嗎?如果可以的話,如何配置?
pip install django-redis apt-get install redis-serv# 在setting添加配置文件 CACHES = {"default": {"BACKEND": "django_redis.cache.RedisCache", # 緩存類型"LOCATION": "127.0.0.1:6379", # ip端口"OPTIONS": {"CLIENT_CLASS": "django_redis.client.DefaultClient", #"CONNECTION_POOL_KWARGS": {"max_connections": 100} # 連接池最大連接數# "PASSWORD": "密碼",}} }# 使用 from django.shortcuts import render,HttpResponse from django_redis import get_redis_connectiondef index(request): # 根據名字去連接池中獲取連接 conn = get_redis_connection("default")conn.hset('n1','k1','v1') # 存數據return HttpResponse('...')46.django路由系統中name的作用?
路由系統中name的作用:反向解析路由字符串
url(r'^home', views.home, name='home')
在模板中使用:{?%?url?'home'?%}
在視圖中使用:reverse(“home”)
47.django的模板中filter和simple_tag的區別?
filter : 類似管道,只能接受兩個參數第一個參數是|前的數據
simple_tag : 類似函數
1、模板繼承:{?%?extends?'layouts.html'?%}
2、自定義方法
????'filter':只能傳遞兩個參數,可以在if、for語句中使用
????'simple_tag':可以無線傳參,不能在if for中使用
????'inclusion_tags':可以使用模板和后端數據
3、防xss攻擊:?'|safe'、'mark_safe'
48.django-debug-toolbar的作用?
一、查看訪問的速度、數據庫的行為、cache命中等信息。?
二、尤其在Mysql訪問等的分析上大有用處(sql查詢速度)
49.django中如何實現單元測試?
對于每一個測試方法都會將setUp()和tearDown()方法執行一遍
會單獨新建一個測試數據庫來進行數據庫的操作方面的測試,默認在測試完成后銷毀。
在測試方法中對數據庫進行增刪操作,最后都會被清除。也就是說,在test_add中插入的數據,在test_add測試結束后插入的數據會被清除。
django單元測試時為了模擬生產環境,會修改settings中的變量,例如, 把DEBUG變量修改為True, 把ALLOWED_HOSTS修改為[*]。
50.解釋orm中 db first 和 code first的含義?
db first: 先創建數據庫,再更新表模型
code first:先寫表模型,再更新數據庫
https://www.cnblogs.com/jassin-du/p/8988897.html
51.django中如何根據數據庫表生成model中的類?
1、修改seting文件,在setting里面設置要連接的數據庫類型和名稱、地址
2、運行下面代碼可以自動生成models模型文件
? ? ? ?- python manage.py inspectdb
3、創建一個app執行下下面代碼:
? ? ? ?- python manage.py inspectdb > app/models.py?
52.使用orm和原生sql的優缺點?
SQL:
# 優點:執行速度快
# 缺點:編寫復雜,開發效率不高
ORM:
# 優點:讓用戶不再寫SQL語句,提高開發效率;可以很方便地引入數據緩存之類的附加功能
# 缺點:在處理多表聯查、where條件復雜查詢時,ORM的語法會變得復雜;沒有原生SQL速度快
53.簡述MVC和MTV
MVC:model(數據庫)、view(模塊)、controller(視圖,控制)
MTV:model(數據庫)、tempalte(視圖)、view(控制)?
54.django的contenttype組件的作用?
contenttype是django的一個組件(app),它可以將django下所有app下的表記錄下來
可以使用他再加上表中的兩個字段,實現一張表和N張表動態創建FK關系。
? ?- 字段:表名稱
? ?- 字段:數據行ID
應用:路飛表結構優惠券和專題課和學位課關聯
Restfull
55.談談你對restfull 規范的認識?
restful其實就是一套編寫接口的'協議',規定如何編寫以及如何設置返回值、狀態碼等信息。
# 最顯著的特點:
# 用restful:?
? ? 給用戶一個url,根據method不同在后端做不同的處理
? ? 比如:post創建數據、get獲取數據、put和patch修改數據、delete刪除數據。
# 不用restful:?
? ? 給調用者很多url,每個url代表一個功能,比如:add_user/delte_user/edit_user/
# 當然,還有協議其他的,比如:
? ? '版本'來控制讓程序有多個版本共存的情況,版本可以放在 url、請求頭(accept/自定義)、GET參數
? ? '狀態碼'200/300/400/500
? ? 'url中盡量使用名詞'restful也可以稱為“面向資源編程”
? ? 'api標示'
? ? ? ? api.luffycity.com
? ? ? ? www.luffycity.com/api/
56.接口的冪等性是什么意思?
'一個接口通過1次相同的訪問,再對該接口進行N次相同的訪問時,對資源不造影響就認為接口具有冪等性。'GET, #第一次獲取結果、第二次也是獲取結果對資源都不會造成影響,冪等。POST, #第一次新增數據,第二次也會再次新增,非冪等。PUT, #第一次更新數據,第二次不會再次更新,冪等。PATCH,#第一次更新數據,第二次不會再次更新,非冪等。DELTE,#第一次刪除數據,第二次不在再刪除,冪等。57.什么是RPC?
'遠程過程調用協議' 是一種通過網絡從遠程計算機程序上請求服務,而不需要了解底層網絡技術的協議。 進化的順序: 現有的RPC,然后有的RESTful規范58.Http和Https的區別?
#Http: 80端口 #https: 443端口 # http信息是明文傳輸,https則是具有安全性的ssl加密傳輸協議。 #- 自定義證書 - 服務端:創建一對證書- 客戶端:必須攜帶證書 #- 購買證書- 服務端: 創建一對證書,。。。。- 客戶端: 去機構獲取證書,數據加密后發給咱們的服務單- 證書機構:公鑰給改機構59.為什么要使用django rest framework框架?
# 在編寫接口時可以不使用django rest framework框架, # 不使用:也可以做,可以用django的CBV來實現,開發者編寫的代碼會更多一些。 # 使用:內部幫助我們提供了很多方便的組件,我們通過配置就可以完成相應操作,如:'序列化'可以做用戶請求數據校驗+queryset對象的序列化稱為json'解析器'獲取用戶請求數據request.data,會自動根據content-type請求頭的不能對數據進行解析'分頁'將從數據庫獲取到的數據在頁面進行分頁顯示。# 還有其他組件:'認證'、'權限'、'訪問頻率控制?60.django rest framework框架中都有那些組件?
#- 路由,自動幫助開發者快速為一個視圖創建4個urlwww.oldboyedu.com/api/v1/student/$www.oldboyedu.com/api/v1/student(?P<format>\w+)$www.oldboyedu.com/api/v1/student/(?P<pk>\d+)/$www.oldboyedu.com/api/v1/student/(?P<pk>\d+)(?P<format>\w+)$ #- 版本處理- 問題:版本都可以放在那里?- url- GET - 請求頭 #- 認證 - 問題:認證流程? #- 權限 - 權限是否可以放在中間件中?以及為什么? #- 訪問頻率的控制匿名用戶可以真正的防止?無法做到真正的訪問頻率控制,只能把小白拒之門外。如果要封IP,使用防火墻來做。登錄用戶可以通過用戶名作為唯一標示進行控制,如果有人注冊很多賬號,則無法防止。 #- 視圖 #- 解析器 ,根據Content-Type請求頭對請求體中的數據格式進行處理。request.data #- 分頁 #- 序列化- 序列化- source- 定義方法- 請求數據格式校驗 #- 渲染器?61.django rest framework框架中的視圖都可以繼承哪些類
a. 繼承APIView(最原始)但定制性比較強這個類屬于rest framework中的頂層類,內部幫助我們實現了只是基本功能:認證、權限、頻率控制,但凡是數據庫、分頁等操作都需要手動去完成,比較原始。class GenericAPIView(APIView)def post(...):pass b.繼承GenericViewSet(ViewSetMixin,generics.GenericAPIView)首先他的路由就發生變化如果繼承它之后,路由中的as_view需要填寫對應關系在內部也幫助我們提供了一些方便的方法:get_querysetget_objectget_serializerget_serializer_classget_serializer_contextfilter_queryset 注意:要設置queryset字段,否則會拋出斷言的異常。代碼 只提供增加功能 只繼承GenericViewSetclass TestView(GenericViewSet):serialazer_class = xxxdef creat(self,*args,**kwargs):pass # 獲取數據并對數據c. 繼承 modelviewset --> 快速快發-ModelViewSet(增刪改查全有+數據庫操作)-mixins.CreateModelMixin(只有增),GenericViewSet-mixins.CreateModelMixin,DestroyModelMixin,GenericViewSet對數據庫和分頁等操作不用我們在編寫,只需要繼承相關類即可。示例:只提供增加功能 class TestView(mixins.CreateModelMixin,GenericViewSet):serializer_class = XXXXXXX *** modelviewset --> 快速開發,復雜點的genericview、apiview62.簡述 django rest framework框架的認證流程。
- 如何編寫?寫類并實現authenticators請求進來認證需要編寫一個類,類里面有一個authenticators方法,我們可以自定義這個方法,可以定制3類返回值。成功返回元組,返回none為匿名用戶,拋出異常為認證失敗。源碼流程:請求進來先走dispatch方法,然后封裝的request對象會執行user方法,由user觸發authenticators認證流程 - 方法中可以定義三種返回值:- (user,auth),認證成功- None , 匿名用戶- 異常 ,認證失敗 - 流程:- dispatch - 再去request中進行認證處理63.django rest framework如何實現的用戶訪問頻率控制??
# 對匿名用戶,根據用戶IP或代理IP作為標識進行記錄,為每個用戶在redis中建一個列表{throttle_1.1.1.1:[1526868876.497521,152686885.497521...],throttle_1.1.1.2:[1526868876.497521,152686885.497521...],throttle_1.1.1.3:[1526868876.497521,152686885.497521...],} 每個用戶再來訪問時,需先去記錄中剔除過期記錄,再根據列表的長度判斷是否可以繼續訪問。'如何封IP':在防火墻中進行設置 -------------------------------------------------------------------------- # 對注冊用戶,根據用戶名或郵箱進行判斷。{throttle_xxxx1:[1526868876.497521,152686885.497521...],throttle_xxxx2:[1526868876.497521,152686885.497521...],throttle_xxxx3:[1526868876.497521,152686885.497521...],} 每個用戶再來訪問時,需先去記錄中剔除過期記錄,再根據列表的長度判斷是否可以繼續訪問。 \如1分鐘:40次,列表長度限制在40,超過40則不可訪問Flask
64.Flask框架的優勢?
Flask自由、靈活,可擴展性強,透明可控,第三方庫的選擇面廣,開發時可以結合最流行最強大的Python庫,
65.Flask框架依賴組件
# 依賴jinja2模板引擎
# 依賴werkzurg協議
66.Flask藍圖的作用
# blueprint把實現不同功能的module分開.也就是把一個大的App分割成各自實現不同功能的module.
# 在一個blueprint中可以調用另一個blueprint的視圖函數, 但要加相應的blueprint名.
67.列舉使用的Flask第三方組件?
# Flask組件
? ? flask-session ?session放在redis
? ? flask-SQLAlchemy 如django里的ORM操作
? ? flask-migrate ?數據庫遷移
? ? flask-script ?自定義命令
? ? blinker ?信號-觸發信號
# 第三方組件
? ? Wtforms 快速創建前端標簽、文本校驗
? ? dbutile ? ? 創建數據庫連接池
? ? gevnet-websocket 實現websocket
# 自定義Flask組件
? ? 自定義auth認證?
? ? 參考flask-login組件
68.簡述Flask上下文管理流程?
# a、簡單來說,falsk上下文管理可以分為三個階段:
1、'請求進來時':將請求相關的數據放入上下文管理中
2、'在視圖函數中':要去上下文管理中取值
3、'請求響應':要將上下文管理中的數據清除
# b、詳細點來說:
1、'請求剛進來':
????????將request,session封裝在RequestContext類中
????????app,g封裝在AppContext類中
????????并通過LocalStack將requestcontext和appcontext放入Local類中
2、'視圖函數中':
????????通過localproxy--->偏函數--->localstack--->local取值
3、'請求響應時':
????????先執行save.session()再各自執行pop(),將local中的數據清除
69.Flask中的g的作用?
# g是貫穿于一次請求的全局變量,當請求進來將g和current_app封裝為一個APPContext類,
# 再通過LocalStack將Appcontext放入Local中,取值時通過偏函數在LocalStack、local中取值;
# 響應時將local中的g數據刪除:
Flask中上下文管理主要涉及到了那些相關的類?并描述類主要作用?
RequestContext ?#封裝進來的請求(賦值給ctx)
AppContext? ? ? ? ?#封裝app_ctx
LocalStack? ? ? ? ? #將local對象中的數據維護成一個棧(先進后出)
Local? ? ? ? ? ? ? ? ? ?#保存請求上下文對象和app上下文對象
為什么要Flask把Local對象中的的值stack 維護成一個列表?
# 因為通過維護成列表,可以實現一個棧的數據結構,進棧出棧時只取一個數據,巧妙的簡化了問題。
# 還有,在多app應用時,可以實現數據隔離;列表里不會加數據,而是會生成一個新的列表
# local是一個字典,字典里key(stack)是唯一標識,value是一個列表
Flask中多app應用是怎么完成?
請求進來時,可以根據URL的不同,交給不同的APP處理。藍圖也可以實現。
????#app1 = Flask('app01')
????#app2 = Flask('app02')
????#@app1.route('/index')
????#@app2.route('/index2')
源碼中在DispatcherMiddleware類里調用app2.__call__,
? 原理其實就是URL分割,然后將請求分發給指定的app。
之后app也按單app的流程走。就是從app.__call__走。
在Flask中實現WebSocket需要什么組件?
?gevent-websocket
wtforms組件的作用?
#快速創建前端標簽、文本校驗;如django的ModelForm
Flask框架默認session處理機制?
# 前提:
? ? 不熟的話:記不太清了,應該是……分兩個階段吧 ??
# 創建:
? ? 當請求剛進來的時候,會將request和session封裝成一個RequestContext()對象,
? ? 接下來把這個對象通過LocalStack()放入內部的一個Local()對象中;
?因為剛開始 Local 的ctx中session是空的;
?所以,接著執行open_session,將cookie 里面的值拿過來,重新賦值到ctx中
? ? (Local實現對數據隔離,類似threading.local)?
# 銷毀:
? ? 最后返回時執行 save_session() 將ctx 中的session讀出來進行序列化,寫到cookie
? ? 然后給用戶,接著把 ctx pop掉
解釋Flask框架中的Local對象和threading.local對象的區別?
# a.threading.local
作用:為每個線程開辟一塊空間進行數據存儲(數據隔離)。
問題:自己通過字典創建一個類似于threading.local的東西。
storage = {
? ?4740: {val: 0},
? ?4732: {val: 1},
? ?4731: {val: 3},
? ?}
# b.自定義Local對象
作用:為每個線程(協程)開辟一塊空間進行數據存儲(數據隔離)。
class Local(object):
? ?def __init__(self):
? ? ? object.__setattr__(self, 'storage', {})
? ?def __setattr__(self, k, v):
? ? ? ident = get_ident()
? ? ? if ident in self.storage:
? ? ? ? ?self.storage[ident][k] = v
? ? ? else:
? ? ? ? ?self.storage[ident] = {k: v}
? ?def __getattr__(self, k):
? ? ? ident = get_ident()
? ? ? return self.storage[ident][k]
obj = Local()
def task(arg):
? ?obj.val = arg
? ?obj.xxx = arg
? ?print(obj.val)
for i in range(10):
? ?t = Thread(target=task, args=(i,))
? ?t.start()
Flask中 blinker 是什么?
# flask中的信號blinker
信號主要是讓開發者可是在flask請求過程中定制一些行為。
或者說flask在列表里面預留了幾個空列表,在里面存東西。
簡言之,信號允許某個'發送者'通知'接收者'有事情發生了
@ before_request有返回值,blinker沒有返回值
# 10個信號
request_started = _signals.signal('request-started') #請求到來前執行
request_finished = _signals.signal('request-finished') #請求結束后執行
before_render_template = _signals.signal('before-render-template')#模板渲染前執行
template_rendered = _signals.signal('template-rendered')#模板渲染后執行
got_request_exception = _signals.signal('got-request-exception') #請求執行出現異常時執行
request_tearing_down = _signals.signal('request-tearing-down')#請求執行完畢后自動執行(無論成功與否)
appcontext_tearing_down = _signals.signal('appcontext-tearing-down')# 請求上下文執行完畢后自動執行(無論成功與否)
appcontext_pushed = _signals.signal('appcontext-pushed') #請求app上下文push時執行
appcontext_popped = _signals.signal('appcontext-popped') #請求上下文pop時執行
message_flashed = _signals.signal('message-flashed')#調用flask在其中添加數據時,自動觸發
SQLAlchemy中的 session和scoped_session 的區別?
# Session:
由于無法提供線程共享功能,開發時要給每個線程都創建自己的session
打印sesion可知他是sqlalchemy.orm.session.Session的對象
# scoped_session:
為每個線程都創建一個session,實現支持線程安全
在整個程序運行的過程當中,只存在唯一的一個session對象。
創建方式:
? ?通過本地線程Threading.Local()
? ?# session=scoped_session(Session)
? ?創建唯一標識的方法(參考flask請求源碼)
SQLAlchemy如何執行原生SQL?
# 使用execute方法直接操作SQL語句(導入create_engin、sessionmaker)
engine=create_engine('mysql://root:*****@127.0.0.1/database?charset=utf8')
DB_Session = sessionmaker(bind=engine)
session = DB_Session()
session.execute('alter table mytablename drop column mycolumn ;')
ORM的實現原理?
# ORM的實現基于一下三點
映射類:描述數據庫表結構,
映射文件:指定數據庫表和映射類之間的關系
數據庫配置文件:指定與數據庫連接時需要的連接信息(數據庫、登錄用戶名、密碼or連接字符串)
DBUtils模塊的作用?
# 數據庫連接池
使用模式:
1、為每個線程創建一個連接,連接不可控,需要控制線程數
2、創建指定數量的連接在連接池,當線程訪問的時候去取,不夠了線程排隊,直到有人釋放(推薦)
---------------------------------------------------------------------------
兩種寫法:
1、用靜態方法裝飾器,通過直接執行類的方法來連接使用數據庫
2、通過實例化對象,通過對象來調用方法執行語句
https://www.cnblogs.com/ArmoredTitan/p/Flask.html
以下SQLAlchemy的字段是否正確?如果不正確請更正:
from datetime import datetime from sqlalchemy.ext.declarative import declarative_base from sqlalchemy import Column, Integer, String, DateTimeBase = declarative_base() class UserInfo(Base):__tablename__ = 'userinfo' id = Column(Integer, primary_key=True, autoincrement=True)name = Column(String(64), unique=True) ctime = Column(DateTime, default=datetime.now()) ----------------------------------------------------------------------- 不正確:Ctime字段中參數應為’default=datetime.now’now 后面不應該加括號,加了的話,字段不會實時更新。SQLAchemy中如何為表設置引擎和字符編碼?
1. 設置引擎編碼方式為utf8。
engine = create_engine("mysql+pymysql://root:123456@127.0.0.1:3306/sqldb01?charset=utf8")
2. 設置數據庫表編碼方式為utf8
class UserType(Base):
__tablename__ = 'usertype'
id = Column(Integer, primary_key=True)
caption = Column(String(50), default='管理員')
# 添加配置設置編碼
__table_args__ = {
'mysql_charset':'utf8'
}
這樣生成的SQL語句就自動設置數據表編碼為utf8了,__table_args__還可設置存儲引擎、外鍵約束等等信息。
SQLAchemy中如何設置聯合唯一索引?
通過'UniqueConstraint'字段來設置聯合唯一索引
__table_args=(UniqueConstraint('h_id','username',name='_h_username_uc'))
#h_id和username組成聯合唯一約束
Tornado
簡述Tornado框架的特點。
異步非阻塞+websocket
簡述Tornado框架中Future對象的作用?
# 實現異步非阻塞 視圖函數yield一個futrue對象,futrue對象默認:self._done = False ,請求未完成self._result = None ,請求完成后返回值,用于傳遞給回調函數使用。tornado就會一直去檢測futrue對象的_done是否已經變成True。如果IO請求執行完畢,自動會調用future的set_result方法:self._result = resultself._done = True 參考:http://www.cnblogs.com/wupeiqi/p/6536518.html(自定義異步非阻塞web框架)Tornado框架中如何編寫WebSocket程序?
Tornado在websocket模塊中提供了一個WebSocketHandler類。 這個類提供了和已連接的客戶端通信的WebSocket事件和方法的鉤子。 當一個新的WebSocket連接打開時,open方法被調用, 而on_message和on_close方法,分別在連接、接收到新的消息和客戶端關閉時被調用。此外,WebSocketHandler類還提供了write_message方法用于向客戶端發送消息,close方法用于關閉連接。Tornado中靜態文件是如何處理的??如: <link href="{{static_url("commons.css")}}" rel="stylesheet" />
# settings.py settings = {"static_path": os.path.join(os.path.dirname(__file__), "static"),# 指定了靜態文件的位置在當前目錄中的"static"目錄下"cookie_secret": "61oETzKXQAGaYdkL5gEmGeJJFuYh7EQnp2XdTP1o/Vo=","login_url": "/login","xsrf_cookies": True, }經上面配置后 static_url()自動去配置的路徑下找'commons.css'文件Tornado操作MySQL使用的模塊?
torndb torndb是基于mysqldb的再封裝,所以使用時要先安裝myqldbTornado操作redis使用的模塊?
tornado-redis簡述Tornado框架的適用場景?
web聊天室,在線投票git
git常見命令作用:
# git init初始化,當前所在的文件夾可以被管理且以后版本相關的數據都會存儲到.git文件中 # git status查看當前文件夾以及子目錄中文件是否發生變化:內容修改/新增文件/刪除,已經變化的文件會變成紅色,已經add的文件會變成綠色 # git add .給發生變化的文件(貼上一個標簽)或 將發生變化的文件放到某個地方,只寫一個句點符就代表把git status中紅色的文件全部打上標簽 # git commit -m新增用戶登錄認證功能以及xxx功能將“綠色”文件添加到版本中 # git log查看所有版本提交記錄,可以獲取版本號 # git reset --hard 版本號 將最新的版本回退到更早的版本 # git reflog 回退到之前版本后悔了,再更新到最新或者最新之前的版本 # git reset --hard 版本 回退簡述以下git中stash命令作用以及相關其他命令。
'git stash':將當前工作區所有修改過的內容存儲到“某個地方”,將工作區還原到當前版本未修改過的狀態 'git stash list':查看“某個地方”存儲的所有記錄 'git stash clear':清空“某個地方” 'git stash pop':將第一個記錄從“某個地方”重新拿到工作區(可能有沖突) 'git stash apply':編號, 將指定編號記錄從“某個地方”重新拿到工作區(可能有沖突) 'git stash drop':編號,刪除指定編號的記錄git 中 merge 和 rebase命令 的區別。
merge: 會將不同分支的提交合并成一個新的節點,之前的提交分開顯示, 注重歷史信息、可以看出每個分支信息,基于時間點,遇到沖突,手動解決,再次提交 rebase: 將兩個分支的提交結果融合成線性,不會產生新的節點; 注重開發過程,遇到沖突,手動解決,繼續操作公司如何基于git做的協同開發?
1、你們公司的代碼review分支怎么做?誰來做? 答:組長創建review分支,我們小功能開發完之后,合并到review分支交給老大(小組長)來看, 1.1、你組長不開發代碼嗎?他開發代碼,但是它只開發核心的東西,任務比較少。或者抽出時間,我們一起做這個事情 2、你們公司協同開發是怎么協同開發的? 每個人都有自己的分支,階段性代碼完成之后,合并到review,然后交給老大看 -------------------------------------------------------------------------- # 大致工作流程 公司:下載代碼git clone https://gitee.com/wupeiqi/xianglong.git或創建目錄 cd 目錄 git init git remote add origin https://gitee.com/wupeiqi/xianglong.gitgit pull origin maste 創建dev分支git checkout dev git pull origin dev 繼續寫代碼git add . git commit -m '提交記錄'git push origin dev 回家: 拉代碼:git pull origin dev 繼續寫:繼續寫代碼git add . git commit -m '提交記錄'git push origin dev如何基于git實現代碼review?
https://blog.csdn.net/june_y/article/details/50817993git如何實現v1.0 、v2.0 等版本的管理?
在命令行中,使用“git tag –a tagname –m “comment”可以快速創建一個標簽。 需要注意,命令行創建的標簽只存在本地Git庫中,還需要使用Git push –tags指令發布到服務器的Git庫中github和gitlab的區別?
如何為github上牛逼的開源項目貢獻代碼?
1、fork需要協作項目 2、克隆/關聯fork的項目到本地 3、新建分支(branch)并檢出(checkout)新分支 4、在新分支上完成代碼開發 5、開發完成后將你的代碼合并到master分支 6、添加原作者的倉庫地址作為一個新的倉庫地址 7、合并原作者的master分支到你自己的master分支,用于和作者倉庫代碼同步 8、push你的本地倉庫到GitHub 9、在Github上提交 pull requests 10、等待管理員(你需要貢獻的開源項目管理員)處理git中 .gitignore文件的作用
一般來說每個Git項目中都需要一個“.gitignore”文件, 這個文件的作用就是告訴Git哪些文件不需要添加到版本管理中。實際項目中,很多文件都是不需要版本管理的,比如Python的.pyc文件和一些包含密碼的配置文件等等。敏捷開發
什么是敏捷開發?
'敏捷開發':是一種以人為核心、迭代、循序漸進的開發方式。它并不是一門技術,而是一種開發方式,也就是一種軟件開發的流程。 它會指導我們用規定的環節去一步一步完成項目的開發。 因為它采用的是迭代式開發,所以這種開發方式的主要驅動核心是人簡述 jenkins 工具的作用?
'Jenkins'是一個可擴展的持續集成引擎。主要用于:持續、自動地構建/測試軟件項目。監控一些定時執行的任務。公司如何實現代碼發布?
nginx+uwsgi+django簡述 RabbitMQ、Kafka、ZeroMQ的區別?
https://blog.csdn.net/zhailihua/article/details/7899006RabbitMQ如何在消費者獲取任務后未處理完前就掛掉時,保證數據不丟失?
為了預防消息丟失,rabbitmq提供了ack 即工作進程在收到消息并處理后,發送ack給rabbitmq,告知rabbitmq這時候可以把該消息從隊列中刪除了。 如果工作進程掛掉 了,rabbitmq沒有收到ack,那么會把該消息 重新分發給其他工作進程。 不需要設置timeout,即使該任務需要很長時間也可以處理。ack默認是開啟的,工作進程顯示指定了no_ack=TrueRabbitMQ如何對消息做持久化?
1、創建隊列和發送消息時將設置durable=Ture,如果在接收到消息還沒有存儲時,消息也有可能丟失,就必須配置publisher confirmchannel.queue_declare(queue='task_queue', durable=True)2、返回一個ack,進程收到消息并處理完任務后,發給rabbitmq一個ack表示任務已經完成,可以刪除該任務3、鏡像隊列:將queue鏡像到cluster中其他的節點之上。 在該實現下,如果集群中的一個節點失效了,queue能自動地切換到鏡像中的另一個節點以保證服務的可用性RabbitMQ如何控制消息被消費的順序?
默認消息隊列里的數據是按照順序被消費者拿走, 例如:消費者1 去隊列中獲取奇數序列的任務,消費者2去隊列中獲取偶數序列的任務。channel.basic_qos(prefetch_count=1) 表示誰來誰取,不再按照奇偶數排列(同時也保證了公平的消費分發)以下RabbitMQ的exchange type分別代表什么意思?如:fanout、direct、topic。
amqp協議中的核心思想就是生產者和消費者隔離,生產者從不直接將消息發送給隊列。 生產者通常不知道是否一個消息會被發送到隊列中,只是將消息發送到一個交換機。 先由Exchange來接收,然后Exchange按照特定的策略轉發到Queue進行存儲。 同理,消費者也是如此。Exchange 就類似于一個交換機,轉發各個消息分發到相應的隊列中。 -------------------------------------------------- type=fanout 類似發布者訂閱者模式,會為每一個訂閱者創建一個隊列,而發布者發布消息時,會將消息放置在所有相關隊列中 type=direct 隊列綁定關鍵字,發送者將數據根據關鍵字發送到消息exchange,exchange根據 關鍵字 判定應該將數據發送至指定隊列。 type=topic 隊列綁定幾個模糊的關鍵字,之后發送者將數據發送到exchange,exchange將傳入”路由值“和 ”關鍵字“進行匹配,匹配成功, 則將數據發送到指定隊列。 --------------------------------------------------- 發送者路由值 隊列中 old.boy.python old.* -- 不匹配 *表示匹配一個 old.boy.python old.# -- 匹配 #表示匹配0個或多個celery
簡述 celery 是什么以及應用場景?
# Celery是由Python開發的一個簡單、靈活、可靠的處理大量任務的分發系統, # 它不僅支持實時處理也支持任務調度。 # http://www.cnblogs.com/wupeiqi/articles/8796552.html簡述celery運行機制。
celery如何實現定時任務?
# celery實現定時任務 啟用Celery的定時任務需要設置CELERYBEAT_SCHEDULE 。 CELERYBEAT_SCHEDULE='djcelery.schedulers.DatabaseScheduler'#定時任務 '創建定時任務' # 通過配置CELERYBEAT_SCHEDULE: #每30秒調用task.add from datetime import timedelta CELERYBEAT_SCHEDULE = {'add-every-30-seconds': {'task': 'tasks.add','schedule': timedelta(seconds=30),'args': (16, 16)}, }簡述 celery多任務結構目錄
pro_cel├── celery_tasks # celery相關文件夾│ ├── celery.py # celery連接和配置相關文件│ └── tasks.py # 所有任務函數├── check_result.py # 檢查結果└── send_task.py # 觸發任務celery中裝飾器 @app.task 和 @shared_task的區別?
# 一般情況使用的是從celeryapp中引入的app作為的裝飾器:@app.task # django那種在app中定義的task則需要使用@shared_task簡述?requests模塊的作用及基本使用?
# 作用: 使用requests可以模擬瀏覽器的請求 # 常用參數:url、headers、cookies、datajson、params、proxy # 常用返回值:contentiter_contenttext encoding="utf-8"cookie.get_dict()簡述 beautifulsoup模塊的作用及基本使用?
# BeautifulSoup 用于從HTML或XML文件中提取、過濾想要的數據形式 #常用方法 解析:html.parser 或者 lxml(需要下載安裝) find、find_all、text、attrs、get簡述 seleninu模塊的作用及基本使用?
Selenium是一個用于Web應用程序測試的工具, 他的測試直接運行在瀏覽器上,模擬真實用戶,按照代碼做出點擊、輸入、打開等操作爬蟲中使用他是為了解決requests無法解決javascript動態問題scrapy
scrapy框架中各組件的工作流程?
#1、生成初始的Requests來爬取第一個URLS,并且標識一個回調函數 第一個請求定義在start_requests()方法內默認從start_urls列表中獲得url地址來生成Request請求, 默認的回調函數是parse方法。回調函數在下載完成返回response時自動觸發 #2、在回調函數中,解析response并且返回值 返回值可以4種:a、包含解析數據的字典b、Item對象c、新的Request對象(新的Requests也需要指定一個回調函數)d、或者是可迭代對象(包含Items或Request) #3、在回調函數中解析頁面內容 通常使用Scrapy自帶的Selectors,但很明顯你也可以使用Beutifulsoup,lxml或其他你愛用啥用啥。 #4、最后,針對返回的Items對象將會被持久化到數據庫通過Item Pipeline組件存到數據庫或者導出到不同的文件(通過Feed exports) http://www.cnblogs.com/wupeiqi/articles/6229292.html在scrapy框架中如何設置代理(兩種方法)?
方式一:內置添加代理功能 # -*- coding: utf-8 -*- import os import scrapy from scrapy.http import Requestclass ChoutiSpider(scrapy.Spider):name = 'chouti'allowed_domains = ['chouti.com']start_urls = ['https://dig.chouti.com/']def start_requests(self):os.environ['HTTP_PROXY'] = "http://192.168.11.11"for url in self.start_urls:yield Request(url=url,callback=self.parse)def parse(self, response):print(response)方式二:自定義下載中間件 import random import base64 import six def to_bytes(text, encoding=None, errors='strict'):"""Return the binary representation of `text`. If `text`is already a bytes object, return it as-is."""if isinstance(text, bytes):return textif not isinstance(text, six.string_types):raise TypeError('to_bytes must receive a unicode, str or bytes ''object, got %s' % type(text).__name__)if encoding is None:encoding = 'utf-8'return text.encode(encoding, errors)class MyProxyDownloaderMiddleware(object):def process_request(self, request, spider):proxy_list = [{'ip_port': '111.11.228.75:80', 'user_pass': 'xxx:123'},{'ip_port': '120.198.243.22:80', 'user_pass': ''},{'ip_port': '111.8.60.9:8123', 'user_pass': ''},{'ip_port': '101.71.27.120:80', 'user_pass': ''},{'ip_port': '122.96.59.104:80', 'user_pass': ''},{'ip_port': '122.224.249.122:8088', 'user_pass': ''},]proxy = random.choice(proxy_list)if proxy['user_pass'] is not None:request.meta['proxy'] = to_bytes("http://%s" % proxy['ip_port'])encoded_user_pass = base64.encodestring(to_bytes(proxy['user_pass']))request.headers['Proxy-Authorization'] = to_bytes('Basic ' + encoded_user_pass)else:request.meta['proxy'] = to_bytes("http://%s" % proxy['ip_port'])配置:DOWNLOADER_MIDDLEWARES = {# 'xiaohan.middlewares.MyProxyDownloaderMiddleware': 543,}scrapy框架中如何實現大文件的下載?
from twisted.web.client import Agent, getPage, ResponseDone, PotentialDataLoss from twisted.internet import defer, reactor, protocol from twisted.web._newclient import Response from io import BytesIOclass _ResponseReader(protocol.Protocol):def __init__(self, finished, txresponse, file_name):self._finished = finishedself._txresponse = txresponseself._bytes_received = 0self.f = open(file_name, mode='wb')def dataReceived(self, bodyBytes):self._bytes_received += len(bodyBytes)# 一點一點的下載self.f.write(bodyBytes)self.f.flush()def connectionLost(self, reason):if self._finished.called:returnif reason.check(ResponseDone):# 下載完成self._finished.callback((self._txresponse, 'success'))elif reason.check(PotentialDataLoss):# 下載部分self._finished.callback((self._txresponse, 'partial'))else:# 下載異常self._finished.errback(reason)self.f.close()scrapy中如何實現限速?
http://scrapy-chs.readthedocs.io/zh_CN/1.0/topics/autothrottle.htmlscrapy中如何實現暫停爬蟲?
# 有些情況下,例如爬取大的站點,我們希望能暫停爬取,之后再恢復運行。 # Scrapy通過如下工具支持這個功能: 一個把調度請求保存在磁盤的調度器 一個把訪問請求保存在磁盤的副本過濾器[duplicates filter] 一個能持續保持爬蟲狀態(鍵/值對)的擴展 Job 路徑 要啟用持久化支持,你只需要通過 JOBDIR 設置 job directory 選項。 這個路徑將會存儲所有的請求數據來保持一個單獨任務的狀態(例如:一次spider爬取(a spider run))。 必須要注意的是,這個目錄不允許被不同的spider 共享,甚至是同一個spider的不同jobs/runs也不行。 也就是說,這個目錄就是存儲一個 單獨 job的狀態信息。scrapy中如何進行自定制命令?
在spiders同級創建任意目錄,如:commands 在其中創建'crawlall.py'文件(此處文件名就是自定義的命令) from scrapy.commands import ScrapyCommandfrom scrapy.utils.project import get_project_settingsclass Command(ScrapyCommand):requires_project = Truedef syntax(self):return '[options]'def short_desc(self):return 'Runs all of the spiders'def run(self, args, opts):spider_list = self.crawler_process.spiders.list()for name in spider_list:self.crawler_process.crawl(name, **opts.__dict__)self.crawler_process.start() 在'settings.py'中添加配置'COMMANDS_MODULE = '項目名稱.目錄名稱'' 在項目目錄執行命令:'scrapy crawlall'scrapy中如何實現的記錄爬蟲的深度?
'DepthMiddleware'是一個用于追蹤每個Request在被爬取的網站的深度的中間件。 其可以用來限制爬取深度的最大深度或類似的事情。 'DepthMiddleware'可以通過下列設置進行配置(更多內容請參考設置文檔):'DEPTH_LIMIT':爬取所允許的最大深度,如果為0,則沒有限制。 'DEPTH_STATS':是否收集爬取狀態。 'DEPTH_PRIORITY':是否根據其深度對requet安排優先scrapy中的pipelines工作原理?
Scrapy 提供了 pipeline 模塊來執行保存數據的操作。 在創建的 Scrapy 項目中自動創建了一個 pipeline.py 文件,同時創建了一個默認的 Pipeline 類。 我們可以根據需要自定義 Pipeline 類,然后在 settings.py 文件中進行配置即可scrapy的pipelines如何丟棄一個item對象?
通過raise DropItem()方法
簡述scrapy中爬蟲中間件和下載中間件的作用?1
http://www.cnblogs.com/wupeiqi/articles/6229292.htmlscrapy-redis組件的作用?
實現了分布式爬蟲,url去重、調度器、數據持久化 'scheduler'調度器 'dupefilter'URL去重規則(被調度器使用) 'pipeline'數據持久化scrapy-redis組件中如何實現的任務的去重?
a.?內部進行配置,連接Redis
b.去重規則通過redis的集合完成,集合的Key為:
???key?=?defaults.DUPEFILTER_KEY?%?{'timestamp':?int(time.time())}
???默認配置:
??????DUPEFILTER_KEY?=?'dupefilter:%(timestamp)s'
c.去重規則中將url轉換成唯一標示,然后在redis中檢查是否已經在集合中存在
???from?scrapy.utils?import?request
???from?scrapy.http?import?Request
???req?=?Request(url='http://www.cnblogs.com/wupeiqi.html')
???result?=?request.request_fingerprint(req)
???print(result) ?# 8ea4fd67887449313ccc12e5b6b92510cc53675c
scrapy-redis的調度器如何實現任務的深度優先和廣度優先?....
簡述 vitualenv?及應用場景?
'vitualenv'是一個獨立的python虛擬環境 如:當前項目依賴的是一個版本,但是另一個項目依賴的是另一個版本,這樣就會造成依賴沖突,而virtualenv就是解決這種情況的,virtualenv通過創建一個虛擬化的python運行環境,將我們所需的依賴安裝進去的,不同項目之間相互不干擾簡述 pipreqs 及應用場景?
可以通過對項目目錄掃描,自動發現使用了那些類庫,并且自動生成依賴清單。pipreqs ./ 生成requirements.txt在Python中使用過什么代碼檢查工具?
1)PyFlakes:靜態檢查Python代碼邏輯錯誤的工具。 2)Pep8: 靜態檢查PEP8編碼風格的工具。 3)NedBatchelder’s McCabe script:靜態分析Python代碼復雜度的工具。 Python代碼分析工具:PyChecker、Pylint簡述 saltstack、ansible、fabric、puppet工具的作用?
?
B Tree和B+ Tree的區別?
1.B樹中同一鍵值不會出現多次,并且有可能出現在葉結點,也有可能出現在非葉結點中。而B+樹的鍵一定會出現在葉結點中,并有可能在非葉結點中重復出現,以維持B+樹的平衡。 2.因為B樹鍵位置不定,且在整個樹結構中只出現一次,請列舉常見排序并通過代碼實現任意三種。
算法基礎之排序
?請列舉常見查找并通過代碼實現任意三種。
無序查找、二分查找、插值查找
請列舉你熟悉的設計模式?
工廠模式/單例模式等有沒有刷過leetcode?
leetcode是個題庫,里面有多很編程題目,可以在線編譯運行。
https://leetcode-cn.com/problemset/all/
列舉熟悉的的Linux命令。
公司線上服務器是什么系統?
linux/centos7
解釋 PV、UV 的含義?
PV訪問量(Page View),即頁面訪問量,每打開一次頁面PV計數+1,刷新頁面也是。
UV訪問數(Unique Visitor)指獨立訪客訪問數,一臺電腦終端為一個訪客。
解釋 QPS的含義?
'QPS(Query Per Second)'每秒查詢率,是對一個特定的查詢服務器在規定時間內所處理流量多少的衡量標準
uwsgi和wsgi的區別?
wsgi是一種通用的接口標準或者接口協議,實現了python web程序與服務器之間交互的通用性。uwsgi:同WSGI一樣是一種通信協議 uwsgi協議是一個'uWSGI服務器'自有的協議,它用于定義傳輸信息的類型, 'uWSGI'是實現了uwsgi和WSGI兩種協議的Web服務器,負責響應python的web請求。supervisor的作用?
# Supervisor: 是一款基于Python的進程管理工具,可以很方便的管理服務器上部署的應用程序。 是C/S模型的程序,其服務端是supervisord服務,客戶端是supervisorctl命令# 主要功能: 1 啟動、重啟、關閉包括但不限于python進程。 2 查看進程的運行狀態。 3 批量維護多個進程。什么是反向代理?
正向代理代理客戶端(客戶端找喲個代理去訪問服務器,服務器不知道你的真實IP) 反向代理代理服務器(服務器找一個代理給你響應,你不知道服務器的真實IP)簡述SSH的整個過程。
SSH 為 'Secure Shell' 的縮寫,是建立在應用層基礎上的安全協議。 SSH 是目前較可靠,為遠程登錄會話和其他網絡服務提供的安全性協議。 利用 SSH 協議可以有效防止遠程管理過程中的信息泄露問題。有問題都去那些找解決方案?
起初是百度,發現搜到的答案不精準,凈廣告 轉戰谷歌,但墻了;搗鼓怎么FQ還會去知乎、stackoverfloow、必應、思否(segmentfault)是否有關注什么技術類的公眾號?
python之禪(主要專注Python相關知識,作者:劉志軍) 碼農翻身(主要是Java的,但不光是java,涵蓋面很廣,作者:劉欣) 實驗樓(在線練項目) and so on最近在研究什么新技術?
Numpy pandas(金融量化分析、聚寬) 百度AI 圖靈API 智能玩具是否了解過領域驅動模型?
Domain-Driven Design?
二進制與十進制之間的轉換
1、十進制 與 二進制之間的轉換
??? (1)、十進制轉換為二進制,分為整數部分和小數部分
整數部分
方法:除2取余法,即每次將整數部分除以2,余數為該位權上的數,而商繼續除以2,余數又為上一個位權上的數。 這個步驟一直持續下去,直到商為0為止,最后讀數時候,從最后一個余數讀起,一直到最前面的一個余數。下面舉例:例:將十進制的168轉換為二進制 得出結果 將十進制的168轉換為二進制,(10101000)2 168 / 2 = 84 -- 0 84 / 2 = 42 -- 0 42 / 2 = 21 -- 0 21 / 2 = 10 -- 1 10 / 2 = 5 -- 05 / 2 = 2 -- 1 2 / 2 = 1 -- 0 1 / 2 = 0 -- 1 二進制(從后往前讀): 10101000小數部分
方法:乘2取整法,即將小數部分乘以2,然后取整數部分,剩下的小數部分繼續乘以2,然后取整數部分, 剩下的小數部分又乘以2,一直取到小數部分為零為止。如果永遠不能為零,就同十進制數的四舍五入一樣, 按照要求保留多少位小數時,就根據后面一位是0還是1,取舍,如果是零,舍掉,如果是1,向入一位。 換句話說就是0舍1入。讀數要從前面的整數讀到后面的整數二進制轉換為十進制 (不分整數和小數部分)
方法:按權相加法,即將二進制每位上的數乘以權,然后相加之和即是十進制數。
例:將二進制數101.101轉換為十進制數。 得出結果:(101.101)2=(5.625)10 在做二進制轉換成十進制需要注意的是 1)要知道二進制每位的權值 2)要能求出每位的值 101.101 轉換為十進制 整數部分:2^2 + 2^0 = 5 小數部分:2^(-1) + 2^(-3) = 1/2 + 1/8 = 0.5 + 0.125 = 0.625 十進制: 2^2 + 2^0 + 2^(-1) + 2^(-3) = 5.625總結
以上是生活随笔為你收集整理的面试之 Python 进阶的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 锋利的jQuery--Ajax(读书笔记
- 下一篇: java如何限制输入值_[限制input