How to Convert Between Binary and Decimal in Batch Script
Unlike hexadecimal (which is written as 0x1A and natively supported by the set /a command), native Batch math does not have built-in support for binary syntax (0b...). To work with binary numbers in a pure Batch environment, you must build explicit loops that perform manual base conversions.
In this guide, we will demonstrate how to manually convert decimal to binary (DecToBin), binary to decimal (BinToDec), and how to use a single-line PowerShell bridge to bypass these limits for larger or negative numbers.
Method 1: Convert Decimal to Binary (Native Batch)
To convert a decimal integer to a binary string, you repeatedly divide the number by 2 and read the remainders (%%). Because we read from the bottom up in the standard algorithm, we prepend the remainder to the left side of our string until the decimal number hits 0.
Implementation Script
@echo off
setlocal enabledelayedexpansion
set "InputDecimal=255"
:: Call the conversion function and store to ResultBinary
call :DecToBin "%InputDecimal%" ResultBinary
echo Base-10 Decimal: %InputDecimal%
echo Base-2 Binary : %ResultBinary%
pause
exit /b 0
:: ==========================================
:: FUNCTION: DecToBin
:: Converts a positive decimal integer into binary.
:: ==========================================
:DecToBin <DecimalInt> <ReturnVar>
setlocal enabledelayedexpansion
set /a num=%~1
set "bin="
:: Handle the explicit 0 case immediately
if %num% equ 0 (
endlocal & set "%~2=0"
exit /b 0
)
:DecToBinLoop
:: %% is the modulo operator (remainder of division)
set /a remainder=num %% 2
:: Divide the number by 2 (batch math truncates decimals automatically)
set /a num=num / 2
:: Prepend the remainder bit to the start of our string
set "bin=!remainder!!bin!"
:: Keep looping until the quotient hits 0
if %num% gtr 0 goto DecToBinLoop
:: Pass the result string back over the setlocal boundary
endlocal & set "%~2=%bin%"
exit /b 0
Because Batch relies on 32-bit signed integers, this pure native script only strictly works for positive numbers from 0 to 2147483647. Handling two's complement mathematics for negative numbers in a pure batch loop is generally unviable, so use PowerShell instead.
Method 2: Convert Binary to Decimal (Native Batch)
To convert a binary string into a decimal number, you read the string one character at a time from left to right. For each bit, you multiply your accumulated total by 2 (effectively shifting the bits one space to the left) and add the current bit (0 or 1).
Implementation Script
@echo off
setlocal enabledelayedexpansion
set "InputBinary=1101"
call :BinToDec "%InputBinary%" ResultDecimal
echo Base-2 Binary : %InputBinary%
echo Base-10 Decimal: !ResultDecimal!
pause
exit /b 0
:: ==========================================
:: FUNCTION: BinToDec
:: Converts a binary string into a decimal integer.
:: ==========================================
:BinToDec <BinaryString> <ReturnVar>
setlocal enabledelayedexpansion
set "binStr=%~1"
set /a dec=0
:BinToDecLoop
:: If the string is empty, we are finished reading
if "!binStr!"=="" goto BinToDecEnd
:: Extract just the very first character (bit)
set "digit=!binStr:~0,1!"
:: Validate that we only got a 1 or a 0
if "!digit!" neq "0" if "!digit!" neq "1" (
echo [ERROR] Invalid binary string detected!
endlocal & set "%~2=ERROR"
exit /b 1
)
:: Shift the accumulator left (* 2) and add the new bit
set /a dec=(dec * 2) + digit
:: Reassign string to exclude the first character we just read
set "binStr=!binStr:~1!"
goto BinToDecLoop
:BinToDecEnd
endlocal & set "%~2=%dec%"
exit /b 0
This bit-shifting mathematical approach is incredibly robust because we never have to track the "power of 2" (e.g., $2^4$, $2^3$) associated with the string length; the successive * 2 operations naturally advance every previous bit into the correct positional value.
Method 3: The PowerShell Bridge ([Convert])
If you need to handle negative integers, two's complement binary strings, or massive 64-bit bounds, trying to script it by hand in Batch is a nightmare. Thankfully, .NET natively supports arbitrary base conversions out-of-the-box. We can capture those results seamlessly in a for /f loop.
Implementation Script
@echo off
setlocal
set "dec_val=42"
set "bin_val=101010"
echo [Method A: Decimal to Binary]
for /f "delims=" %%I in ('powershell -NoProfile -Command "[Convert]::ToString(%dec_val%, 2)"') do (
set "ps_bin=%%I"
)
echo Decimal "%dec_val%" is Binary "%ps_bin%"
echo.
echo [Method B: Binary to Decimal]
:: ToInt32 automatically assumes the string is signed two's complement
:: if the 32nd bit is set. (E.g. 1111...1111 = -1)
for /f "delims=" %%I in ('powershell -NoProfile -Command "[Convert]::ToInt32('%bin_val%', 2)"') do (
set "ps_dec=%%I"
)
echo Binary "%bin_val%" is Decimal "%ps_dec%"
pause
exit /b 0
Best Practices
- Beware the 32-Bit Ceiling: The maximum positive number
set /acan handle in Batch is2147483647(which is01111111 11111111 11111111 11111111in binary). Passing a 32-character binary string with a1at the very front to theBinToDecBatch function will trigger an integer overflow crash and return garbage numbers. If you need standard 64-bit logic, use the PowerShell[Convert]::ToInt64('str', 2)bridge. - Handle Input Validation: The native
BinToDecloop must protect itself against malformed variables. If a user accidentally typed1020as the input string, standard mathematical bit-shifting logic would output entirely wrong configurations. Theif "!digit!" neq...guard guarantees data integrity. - Delayed Expansion: Notice that the
BinToDecandDecToBinfunctions enabledelayedexpansionat theirsetlocalbarrier and operate entirely using!var!bounds instead of%var%. This absolutely prevents variable parsing crashes inside thegotorecursive block.
Conclusion
Understanding how to convert bases empowers your scripts to handle bitwise operator payloads, modify IP octet math directly, or decipher raw bitmasks queried from wmic. While pure Batch can simulate this math through controlled set /a strings and recursive loops, the PowerShell [Convert] object is the professional approach for any edge case exceeding positive 32-bit scope.