您好,登錄后才能下訂單哦!
今天就跟大家聊聊有關Python版本低導致Pip無法使用怎么解決,可能很多人都不太了解,為了讓大家更加了解,小編給大家總結了以下內容,希望大家根據這篇文章可以有所收獲。
終于下決心把python從2.7升到了3.7。懶人安裝當然使用Anaconda。
安裝成功,編譯成功。但是用pip 安裝包的時候提示:
pip is configured with locations that require TLS/SSL, however the ssl module in Python is not available。
原因是python3.7為了安全性考慮,要求使用openssl 1.0.2之后的版本。但是自帶的openssl,版本是1.0.1。
解決辦法:
重裝一下openssl
進入
Anaconda Prompt:
conda install -c anaconda openssl
就一切解決了哈啊哈!完美!
補充知識:Python3使用multiprocessing多進程模塊共享變量
在使用Python用CPU跑一個人臉識別的模塊,神經網絡的計算比較耗時,因為Python GIL的限制,因此這里使用多進程來并行跑數據集。
在多個進程之間共享簡單變量
有很多張人臉圖片,現在使用8個進程來分別對人臉圖片進行識別,但是要知道總的進度和正確率,因此這里要在各個進程之間共享變量。這里需要的只是整型無符號變量。
在對總的進度和準確率進行計算的時候要加鎖,防止別的進程改變
在使用 print輸出的時候要加鎖,因為控制臺也是資源,要防止搶占
加鎖了之后要記得釋放鎖
假設8個進程共識別了count張圖片,然后正確的圖片有correct張。思路如下:
在主進程中聲明要共享的count和correct變量,初始化進程的時候傳入
在各個進程中識別一張圖片count就自增1,識別正確的話correct也要自增1,自增的時候要加鎖
控制臺輸出相關信息的時候也要加鎖
# l代表長整型無符號變量 count = multiprocessing.Value('l', 0) correct = multiprocessing.Value('l', 0) lock = multiprocessing.Lock() # 要運行的函數為run(),lis為劃分給每個進程的識別圖片列表 p = [multiprocessing.Process(target=run, args=(lock, i, count, correct)) for i in lis] for i in p: i.start() for i in p: i.join()
在run函數中:
# 多個線程對共享變量進行操作,加鎖 lock.acquire() # 圖片已經識別完畢,總數加一 count.value += 1 # 下面兩個if分別為識別正確的情況 if i[0] == 3 and dis >= threshold: correct.value += 1 print("正確率:{0:.5f} 總數:{1} 正確數:{2} 錯誤數:{3} 參數個數:{4} 向量夾角:{5:.5f} 圖片1:{6} 圖片2:{7}".format(correct.value/count.value, count.value, correct.value, count.value-correct.value, i[0], dis[0], i[1], i[2])) lock.release() continue if i[0] == 4 and dis < threshold: correct.value += 1 print("正確率:{0:.5f} 總數:{1} 正確數:{2} 錯誤數:{3} 參數個數:{4} 向量夾角:{5:.5f} 圖片1:{6} 圖片2:{7}".format(correct.value/count.value, count.value, correct.value, count.value-correct.value, i[0], dis[0], i[1], i[2])) lock.release() continue print("識別錯誤:參數個數:{0} 向量夾角:{1} 圖片1:{2} 圖片2:{3}".format(i[0], dis[0], i[1], i[2])) # 不要遺漏解鎖,否則進程會死鎖 lock.release()
在多個進程中共享字典dict
準備把識別過的照片特征緩存起來,因此這里使用字典,key就是照片名稱,value就是特征值。在此使用mutiprocessing.Manage()來實現。
manager = multiprocessing.Manager() # 這個是用來在多個進程中間共享的字典 sync_dict = manager.dict() # 這個是使用pickle序列化到文件中用的臨時字典變量 mem_dict = dict() # 如果存在字典就載入,使用臨時字典中轉是因為sysnc_dict直接序列化會在下次加載時導致Manager在多個進程中的連接出現問題 if os.path.exists("./muti_thread_mem.pkl"): with open("./muti_thread_mem.pkl", "rb") as f: mem_dict = pickle.load(f) for i in mem_dict: sync_dict[i] = mem_dict[i]
使用multiprocessing.Manager()時就不用加鎖了,它本身帶有同步的功能。在run函數中直接使用就好了。
if i[1] in sync_dict: # 有記錄就直接讀取緩存 encoding1 = sync_dict[i[1]] else: # 沒記錄就計算出來再緩存一下 face.file = Image.open(prefix+i[1]) encoding1 = face.encodings sync_dict[i[1]] = encoding1 if i[2] in sync_dict: encoding2 = sync_dict[i[2]] else: face.file = Image.open(prefix+i[2]) encoding2 = face.encodings sync_dict[i[2]] = encoding2
如果緩存過就直接讀取,如果沒有緩存過就計算后然后再緩存一下,便于下次讀取。大多都是業務的邏輯,沒有什么意思。算完了之后在主程序退出之前再緩存到本地就好了。
with open("./muti_thread_mem.pkl", 'wb') as f: for k, v in enumerate(sync_dict): mem_dict[v] = sync_dict[v] if len(mem_dict): # 傳入的4就是想試一下Python新版本的特性而已,沒啥其他意思 pickle.dump(mem_dict, f, 4)
坑
在Pycharm里面運行代碼的時候會碰到一些問題。
使用Pycharm的Python console運行代碼的時候會導致一個進程完成任務之后,join等待主線程退出的時候,所有進程都報錯pipe broken連接不到Manager的共享字典。但是使用本地Terminal運行的時候,一個進程完成任務后是不會導致其他進程報錯的,因此推斷這里是Pycharm的坑。
關鍵字:multiprocessing.Manager()報錯pipe broken,進程獲取共享變量時異常,導致所有進程退出
調試代碼(Pycharm debug模式)的時候也會導致調試過程中進程連接不到Manager的共享字典變量。
這些坑都涉及到Manager在共享變量時使用的客戶端/服務端模式,最后socket連接報錯,所有進程讀取共享變量時報錯退出。我這次的解決方式是不要啟用Pycharm的Python console來運行代碼就好了。
看完上述內容,你們對Python版本低導致Pip無法使用怎么解決有進一步的了解嗎?如果還想了解更多知識或者相關內容,請關注億速云行業資訊頻道,感謝大家的支持。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。