batch rechnen mit prozenten?

2 Antworten

Vom Fragesteller als hilfreich ausgezeichnet

Willst du zum Beispiel 25% von einer Variablen abziehen:

set /a zahl    = 200
set /a percent = 25
set /a zahl   -= zahl * percent / 100

beachte dabei, dass du mit set /a nur mit Integern rechnen kannst, bei

set /a zahl    = 7
set /a percent = 25
set /a zahl   = zahl * percent / 100

käme zum Beispiel 6 raus, da bei 1.75 alles nach dem Komma "weggelassen" wird und cmd demnach 7 - 1 = 6 rechnet.

Um das zumindest teilweise zu umgehen könntest du erst am Ende durch 100 teilen:

set /a zahl    = 7
set /a percent = 25
set /a zahl    = (zahl*100) - (zahl*percent)
set /a zahl   /= 100

Dadurch kommt jetzt eigentlich immer das richtige Ergebnis raus, aber halt mit abgeschnittenen Kommazahlen. (In diesem Fall 5 statt 5.25)

Um jetzt die wirklich richtige Zahl zu bekommen muss man noch etwas weiter gehen:

Ich habe dazu mal einen eigenen "Batch-Befehl" geschrieben: github.com/timlg07/Batch_Tools/3-2-division.cmd

Wie du die Datei benutzt erfährst du hier (github.com/timlg07/Batch_Tools/3-2-division.txt) und alle Infos zur Syntax erfährst du so:

divide/?

Du könntest das obige Beispiel dann mit dem divide Befehl ergänzen:

set /a zahl    = 7
set /a percent = 25
set /a zahl    = (zahl*100) - (zahl*percent)
divide %zahl%/100

Um das dann wieder in eine Variable einzulesen:

set /a zahl    = 7
set /a percent = 25
set /a zahl    = (zahl*100) - (zahl*percent)
for /f %%e in ('divide %zahl%/100') do set zahl=%%e

So hast du in %zahl% nun endlich die 5.25!

Falls du noch nicht mit GitHub gearbeitet hast und dir das zu kompliziert ist, einfach folgenden Code in eine Batch kopieren (wenn du die gleich divide.cmd nennst, musst du sie vor dem verwenden auch nicht mehr ausführen)

@echo off & setlocal enableDelayedExpansion
if "%1"=="" goto noArgs

echo.%* | find /I "/?" >nul && goto info
echo.%* | find /I "/HELP" >nul && goto info

for /F "tokens=1* delims=/" %%A in ("%~1") do (
	set "dividend=%%A"
	set "divisor=%%B"
)

if not defined dividend set dividend=NAN
if not defined divisor  set  divisor=NAN

if not "%~2"=="" ( set "decimalPlaces=%~2"    ) else ( set "decimalPlaces=6"    )
if not "%~3"=="" ( set "decimalSeperator=%~3" ) else ( set "decimalSeperator=." )


call :expand dividend
call :expand divisor

call :checkNumber dividend
call :checkNumber divisor
call :checkNumber decimalPlaces


call :division
echo %result%
exit /B

:expand
	set "%~1=!%~1:RANDOM=%random%!"
	set "%~1=!%~1:MAX=2147483647!"
	set "%~1=!%~1:PI=3!"&rem 3.141592654
	set "%~1=!%~1:E=3!" &rem 2.718281828
exit /B

:checkNumber
	call :trim "%~1"

	set "varName=%~1"
	set "varCont=!%~1!"
	set /a varContNumber=varCont

	if %varContNumber% EQU 0 (
		if not "%varCont:0=%"=="" (
			call :onError NAN %varName%
			set /a varCont=1
		)
	)
	call :deleteLeadingZero "%varCont%"
	set "%varName%=%errorlevel%"
exit /B

:trim
	set "%~1=!%~1: =!"
exit /B

:deleteLeadingZero
exit /B %~1

:onError
	if /I "%~1"=="NAN" (
	    echo ERROR_NAN at checkNumber
		echo "!%~2!" is not a number.
	)
exit /B


:division
	
	set /a int= dividend / divisor
	set "result=%int%%decimalSeperator%"
	set /a remainder=dividend-(int*divisor)
	set /a decP=0
	:div_LOOP
		set /a intR=(remainder*10)/divisor
		set /a remainder=(remainder*10)-(intR*divisor)
		set result=%result%%intR%
		set /a decP+=1
		if %remainder% EQU 0 exit /b 0
		if %decP% GEQ %decimalPlaces% exit /b 1
	goto div_LOOP
exit /B

	
:noArgs
	echo Keine Argumente.
	echo weitere Infos: divide /?
goto checkName

:info
	echo.
	echo Syntax:
	echo.
	echo DIVIDE Integer/Integer [decimalPlaces [decimalSeperator]]
	echo.
	echo.
	echo Returns an float value with the given
	echo amount of decimal places. (Default:6)
	echo.
	echo The decimal seperator can be "." or "," 
	echo or any other character. (Default:".")
	echo.
	echo Following variables can be used:
	echo RANDOM ^| expands to a random integer
	echo MAX    ^| expands to the integer max value
	echo PI     ^| expands to the value of pi
	echo E      ^| expands to the value of e
	echo.
	echo (PI and E are both 3 because floats in input are not supported yet)
	echo.
exit /b

:checkName
	if /i not "%~n0"=="DIVIDE" copy "%~nx0" "divide%~x0" >nul
exit /B

~Tim

Woher ich das weiß:Hobby
timlg07  03.10.2018, 14:05

Falls Interesse besteht schreib ich n Tool, welches doubles als String speichert und damit dann alle Grundrechenarten durchführen kann.

1
Jesaja01 
Fragesteller
 03.10.2018, 22:31

Danke! Bin grad leicht überfordert xD werd mich die Tage mal durcharbeiten jetzt freu ich mich erst mal auf Schule morgen. : l

1
timlg07  15.10.2018, 22:20
@Jesaja01

und hat des mit GitHub geklappt, oder hast einfach die Version ohne Kommazahlen genommen?

0
Jesaja01 
Fragesteller
 16.10.2018, 21:08
@timlg07

Ich habs noch nicht hinbekommen das ich "divide" benutzen kann oder wie ich meinem script sagen kann das es "da mal vorbeischauen soll" : p wenn du mir da noch kurz helfen könntest ?!

0
timlg07  17.10.2018, 22:29
@Jesaja01

Am einfachsten wird es sein, wenn du den Code von oben in eine divide.cmd Datei packst und diese dann in das Verzeichnis deiner Batch oder am besten in den system32 Ordner o.ä. legst. Dann kannst du den Befehl wie in den vorigen Codebeispielen verwenden.

0
timlg07  19.10.2018, 13:42

kleines Update: mit der neusten Version können die Argumente auch Rechnungen enthalten, du musst einfache Plus/Minus/Mal Rechnungen jetzt nicht mehr separat davor machen, sondern kannst zum Beispiel

divide (8-1)/10

eingeben, um 7/10 zu rechnen.

0

Mit grundlegenden Kenntnissen über die Prozentrechnung braucht man sowas nicht. Z.b. zieht man 5% von einer Zahl ab, indem man mit 0.95 multipliziert.

Jesaja01 
Fragesteller
 02.10.2018, 19:31

Das wär ne Idee xD Danke. Aber trotzdem, für was ist das das "%" bei Opperatoren

0
FireEraser  02.10.2018, 19:33
@Jesaja01

Das ist der Modulo-Operator, damit wird der Rest einer Division berechnet.

2
Jesaja01 
Fragesteller
 02.10.2018, 19:38
@FireEraser

Nein warte mir ist gerade aufgefallen was an Batch so toll ist... Man kann nicht zu Single oder double wechseln sondern nur min int arbeiten : ( Deswgen hat das nicht geklappt. Trotsdem dnke : )

0