Check all drives (letter and free size) and compar

2019-08-01 07:44发布

问题:

I have problem for comparing high numbers of the PC disks.

Script:

for /f "tokens=* delims== skip=1" %%x in ('"wmic.exe logicaldisk where DriveType=3 get DeviceID,FreeSpace,Size"') do (
    for /f "tokens=1-3" %%a in ("%%x") do (
        set "DiskID=%%a" & set "DiskFree=%%b"
        if !DiskFree! gtr !DiskFreeFinal! Set "DiskIDFinal=!DiskID!" && set "DiskFreeFinal=!DiskFree!"
    )
)
echo Biggest free space is on drive: %DiskIDFinal% (%DiskFreeFinal%)

Output is bad size comparing not real.

回答1:

An accompanying PowerShell answer, (despite the lack of an appropriate tag), for informational and comparison purposes.

$FixedDisks = Get-WMIObject -Query "Select DeviceID,FreeSpace From Win32_LogicalDisk Where DriveType='3'"
$MostFreeSpace = 0
$MostName = "Null"
ForEach ( $Disk In $FixedDisks ) {
    If ( $Disk.FreeSpace -GT $MostFreeSpace ) {
        $MostFreeSpace = $Disk.FreeSpace
        $MostName = $Disk.DeviceID
    }
}
Write-Host "Biggest free space is on drive: $MostName ($MostFreeSpace)"


回答2:

Your batch reworked to do string based comparisons for large numbers (up to 88817 PetaByte)

:: Q:\Test\2018\06\27\SO_51057439.cmd
@Echo off&SetLocal EnableDelayedExpansion
Set "Space=                    "
Set "DiskFreeFinal=%Space%"
for /f "tokens=* delims== skip=1" %%x in (
  '"wmic.exe logicaldisk where DriveType=3 get DeviceID,FreeSpace,Size"'
) do for /f "tokens=1-3" %%a in ("%%x") do (
    set "DiskFree=%Space%%%b"
    Rem Echo %%a !DiskFree:~-20!
    if "!DiskFree:~-20!" gtr "!DiskFreeFinal:~-20!" (
        set "DiskIDFinal=%%a"
        set "DiskFreeFinal=!DiskFree!"
    )
)
echo Biggest free space is on drive: %DiskIDFinal% (%DiskFreeFinal: =%)

Sample output (including the REMed out line):

> .\SO_51057439.cmd
A:           1049407488 1049407488
C:         113724567552 113724567552
D:        1090293293056 1090293293056
G:         778550509568 778550509568
H:             68505600 68505600
Biggest free space is on drive: D: (1090293293056)


回答3:

You could left-zero-pad the numbers to compare to the same width and do string comparison then:

@echo off
setlocal EnableDelayedExpansion
set "DiskIDFinal=" & set "DiskFreeFinal=000000000000000000000000"
for /F "skip=1 delims=" %%x in ('"wmic.exe logicaldisk where DriveType=3 get DeviceID,FreeSpace,Size"') do (
    for /F "tokens=1-3" %%a in ("%%x") do (
        rem // Pad number with 24 zeros to the left, then compare the right-most 24 digits:
        set "DiskID=%%a" & set "DiskFree=000000000000000000000000%%b"
        if "!DiskFree:~-24!" gtr "!DiskFreeFinal:~-24!" (
            set "DiskIDFinal=!DiskID!" & set "DiskFreeFinal=!DiskFree:~-24!"
        )
    )
)
rem // Remove leading zeros from final number:
for /F "tokens=* delims=0" %%z in ("!DiskFreeFinal!") do set "DiskFreeFinal=%%z"
if not defined DiskFreeFinal set "DiskFreeFinal=0"

echo Biggest free space is on drive: %DiskIDFinal% (%DiskFreeFinal%)
endlocal

Alternatively, you could split the numbers into two parts and compare them individually:

@echo off
setlocal EnableDelayedExpansion
set "DiskIDFinal="
set /A "DiskFreeFinalHi=0, DiskFreeFinalLo=0"
for /F "skip=1 delims=" %%x in ('"wmic.exe logicaldisk where DriveType=3 get DeviceID,FreeSpace,Size"') do (
    for /F "tokens=1-3" %%a in ("%%x") do (
        set "DiskID=%%a" & set "DiskFreeLo=%%b"
        rem // Split number into two parts for the right part to have 9 digits:
        set "DiskFreeHi=!DiskFreeLo:~,-9!" & set "DiskFreeLo=!DiskFreeLo:~-9!"
        for /F "tokens=* delims=0" %%z in ("!DiskFreeLo!") do set "DiskFreeLo=%%z"
        set /A "DiskFreeHi+=0, DiskFreeLo+=0"
        if !DiskFreeHi! gtr !DiskFreeFinalHi! (
            set "DiskIDFinal=!DiskID!"
            set /A "DiskFreeFinalHi=DiskFreeHi, DiskFreeFinalLo=DiskFreeLo"
        ) else if !DiskFreeHi! equ !DiskFreeFinalHi! (
            if !DiskFreeLo! gtr !DiskFreeFinalLo! (
                set "DiskIDFinal=!DiskID!"
                set /A "DiskFreeFinalHi=DiskFreeHi, DiskFreeFinalLo=DiskFreeLo"
            )
        )
    )
)
rem // Recombine the two parts of the number:
set "DiskFreeFinalLo=000000000%DiskFreeFinalLo%"
for /F "tokens=* delims=0" %%z in ("%DiskFreeFinalHi%%DiskFreeFinalLo:~-9%") do set "DiskFreeFinal=%%z"
if not defined DiskFreeFinal set "DiskFreeFinal=0"

echo Biggest free space is on drive: %DiskIDFinal% (%DiskFreeFinal%)
endlocal