Jun 29, 2013

Function: LargeInt_mul

I wrote it some time ago but I needed to assure myself it works decently. It receives three parameters: two names of variables with components and third variable name for the result. I plan to add another improvement that would increase calculating speed greatly - I will publish it as I have it done. As always, no warranty is given.
@echo off
:loop
echo.
echo  give two big integers to be multiplied : 
set/p first=give first number : 
set/p second=give second number : 
call:LargeInt_mul first second first
if "%errorlevel%"=="1" (echo  Too few parameters.) else (echo [%first%])
pause
goto loop
:handle_buff
if %buff% GTR 9 (set buff=%buff:~-1%&set carry=%buff:~0,1%) else (set carry=)
exit/b0
:LargeInt_mul
setlocal
set left=%% %1 %%
set left=%left: =%
call set left=%left%
set right=%% %2 %%
set right=%right: =%
call set right=%right%
if defined left (if defined right (goto lrgintmul))
set exitcode=1
goto lrgintmul_endproc
:lrgintmul
set upper_component=%left%
set lower_component=%right%
:lrgintmul_loop
set temp_component_l=
set temp_component_u=
set temp_component_l=%lower_component:~-1%
set temp_component_u=%upper_component:~-1%
if defined temp_component_l (
 if "%temp_component_l%"=="0" (set step=1&goto increase_suffix)
 if defined temp_component_u (
  set/a buff=%temp_component_l%*%temp_component_u%
  if defined carry (set/a buff+=%carry%)
  call:handle_buff
 )
)
if "%suffix_added%"=="false" (
 set subst=%buff%%subst%%suffix%
) else (
 set subst=%buff%%subst%
)
set suffix_added=true
set upper_component=%upper_component:~0,-1%
if not defined upper_component (
 if defined carry (
  set subst=%carry%%subst%&set carry=
 )
)
if not defined upper_component (
 if not defined lower_component (
  goto lrgintmul_opsucc
 )
 set add_chain=%add_chain%;%subst%
 :increase_suffix
 set subst=
 set upper_component=%left%
 set lower_component=%lower_component:~0,-1%
 set suffix_added=false
 set suffix=%suffix%0
 if "%step%"=="1" (set step=&goto lrgintmul_loop_)
)
:lrgintmul_loop_
if defined lower_component (goto lrgintmul_loop)
set sum=0
for %%A in (%add_chain%) do (set component=%%A&call:LargeInt_add sum component sum)
:lrgintmul_opsucc
set exitcode=0
:lrgintmul_endproc
call:ThrowErrorLevel exitcode %exitcode%
endlocal&set %3=%sum%&exit/b%errorlevel%


:LargeInt_add
setlocal
set left=%% %1 %%
set left=%left: =%
call set left=%left%
set right=%% %2 %%
set right=%right: =%
call set right=%right%
if defined left (if defined right (goto lrgintadd))
set exitcode=1
goto lrgintadd_endproc
:lrgintadd
set buff=
set lastchar_l=
set lastchar_r=
if defined left (set lastchar_l=%left:~-1%)
if defined right (set lastchar_r=%right:~-1%)
if defined carry (set/a buff+=%carry%&set carry=)
if defined lastchar_l (set/a buff+=%lastchar_l%)
if defined lastchar_r (set/a buff+=%lastchar_r%)
if %buff% GTR 9 (
 set outvar=%buff:~-1%%outvar%
 set carry=%buff:~0,1%
) else (
 set outvar=%buff%%outvar%
)
if defined left (set left=%left:~0,-1%)
if defined right (set right=%right:~0,-1%)
if not defined left (if not defined right (set outvar=%carry%%outvar%&goto lrgintadd_opsucc))
goto lrgintadd
:lrgintadd_opsucc
set exitcode=0
:lrgintadd_endproc
call:ThrowErrorLevel exitcode %exitcode%
endlocal&set %3=%outvar%&exit/b%errorlevel%
:ThrowErrorLevel
if defined %1 set %1=
exit/b%2

No comments:

Post a Comment