今度は、ふつうにエラトステネスのふるい的に約数の和を求めました。ただし、変数の数が多くなると遅くなるので、まず最小の素因数を記録しておいて、そこに約数の和を上書きする方法を取ります。それでも、10000も変数があると非常に遅くなります。今回は7分半かかりました。
@echo off call :start_time setlocal enabledelayedexpansion set /a N = 10000 set /a M = %N% - 1 set /a s = 0 set /a sqrt = 1 for /L %%n in (2, 1, %M%) do ( set /a _s = !sqrt! + 1 set /a sq = !_s! * !_s! if !sq! LEQ %%n set /a sqrt += 1 call :f %%n !sqrt! if !ERRORLEVEL! GTR %%n ( if !ERRORLEVEL! LSS %N% ( set /a n1 = !ERRORLEVEL! set /a s0 = !n1! / !sqrt! call :sqrt !n1! !s0! call :f !n1! !ERRORLEVEL! if !ERRORLEVEL! == %%n ( set /a s += %%n + !n1! ) ) ) ) echo %s% call :check_time exit /b 0 :f setlocal set /a s = 1 for /L %%d in (2, 1, %2) do ( set /a r = %1 %% %%d if !r! == 0 ( set /a d2 = %1 / %%d if %%d == !d2! ( set /a s += %%d ) else ( set /a s += %%d + !d2! ) ) ) exit /b %s% :sqrt setlocal set /a r = %2 :loop_sqrt set /a r1 = (%r% + %1 / %r%) / 2 if %r1% GEQ %r% exit /b %r% set /a r = %r1% goto :loop_sqrt :start_time call :get_time set /a __t0 = %ERRORLEVEL% exit /b 0 :check_time setlocal call :get_time set /a t = %ERRORLEVEL% - %__t0% if %t% LSS 10 ( echo 0.0%t%s ) else ( if %t% LSS 100 ( echo 0.%t%s ) else ( echo %t:~0,-2%.%t:~-2%s ) ) exit /b 0 :get_time setlocal set t=%TIME% set /a h = %t:~0,2% set /a m = 1%t:~3,2% %% 100 set /a s = 1%t:~6,2% %% 100 set /a ss = 1%t:~-2% %% 100 set /a ret = ((%h% * 60 + %m%) * 60 + %s%) * 100 + %ss% exit /b %ret%