如何使用python在Windows上查找未分配的驱动器号

时间:2018-12-04 07:24:41

标签: python windows windows-shell network-drive

我需要通过python脚本在Windows上找到一个免费的驱动器号。 Free代表未分配给任何物理或远程设备。

我做了一些研究,并在这里找到了关于stackoverflow的解决方案(请记住确切的链接):

show table status WHERE NAME = 'crm_Pipeline';

这对所有物理驱动器和连接的网络驱动器都适用。但不适用于当前断开连接的驱动器。 如何获得所有用过的驱动器号,以及临时用过的驱动器号?

2 个答案:

答案 0 :(得分:1)

因为我将找到的字母传递给外部脚本,该脚本将运行Winshell cmd'subst / d letter '。我不能传递当前未安装的驱动器,因为它会删除网络驱动器映射。

我发现的唯一方法是winshellcmd“ net use”查找不可用驱动器的结果。

这是我的解决方案,如果您有更好的方法,请与我分享:

# for python 2.7
import string
import win32api
from subprocess import Popen, PIPE

def _getnetdrives():
""" As _getfreedriveletter can not find unconnected network drives
    get these drives with shell cmd 'net use' """
    callstr = 'net use'
    phandle = Popen(callstr, stdout=PIPE)
    presult = phandle.communicate()
    stdout = presult[0]
    # _stderr = presult[1]
    networkdriveletters = []
    for line in stdout.split('\n'):
        if ':        ' in line:
             networkdriveletters.append(line.split()[1] + '\\')
    return networkdriveletters

def getfreedriveletter():
    """ Find first free drive letter """
    assigneddrives = win32api.GetLogicalDriveStrings().split('\000')[:-1]
    assigneddrives = assigneddrives + _getnetdrives()
    assigneddrives = [item.rstrip(':\\').lower() for item in assigneddrives]
    for driveletter in list(string.ascii_lowercase[2:]): #array starts from 'c' as i dont want a and b drive
        if not driveletter in assigneddrives:
        return driveletter.upper() + ':'

答案 1 :(得分:1)

创建子进程相对昂贵,并且解析自由格式的文本输出并不是最可靠的技术。您可以改用PyWin32来调用与net use相同的API函数。

import string
import win32api
import win32wnet
import win32netcon

def get_free_drive():
    drives = set(string.ascii_uppercase[2:])
    for d in win32api.GetLogicalDriveStrings().split(':\\\x00'):
        drives.discard(d)
    # Discard persistent network drives, even if not connected.
    henum = win32wnet.WNetOpenEnum(win32netcon.RESOURCE_REMEMBERED, 
        win32netcon.RESOURCETYPE_DISK, 0, None)
    while True:
        result = win32wnet.WNetEnumResource(henum)
        if not result:
            break
        for r in result:
            if len(r.lpLocalName) == 2 and r.lpLocalName[1] == ':':
                drives.discard(r.lpLocalName[0])
    if drives:
        return sorted(drives)[-1] + ':'

请注意,此函数返回最后一个可用的驱动器号。通常的做法是,从列表的末尾开始分配映射驱动器和替代驱动器(例如从net.exe和subst.exe),并从头开始分配本地系统驱动器。