Board logo

标题: 【练习-041】批处理平分时钟数字 [打印本页]

作者: batman    时间: 2009-4-9 00:06     标题: 【练习-041】批处理平分时钟数字

&&有一道小学三年级数学题如下:
   用一根过钟心的直线将时钟钟面平分为两半,要求平分的两面上的时钟数字和相等。
   现在我要求大家用批处理来解这首题,列出平分后两边的两组钟面数字(提示数字为1-12)。
   满分10分,视代码具体情况加分(以思路为重)。

[ 本帖最后由 batman 于 2009-4-10 11:55 编辑 ]
作者: lhjoanna    时间: 2009-4-9 00:33

思路一般,事先考虑好各组存在的位置。也适用于24小时制时钟。
  1. @echo off&setlocal enabledelayedexpansion
  2. :begin
  3. set /p "_time=请输入时钟制:"
  4. if not "!_time!" equ "12" (
  5.    if not  "!_time!" equ "24"  goto begin
  6. )
  7. set /a a=_time/4,b=a*3
  8. for /l %%i in (1 1 %_time%) do (
  9.     if %%i leq %a% (
  10.         set "group1=!group1! %%i"
  11.     ) else if %%i leq %b% (
  12.            set "group2=!group2! %%i"
  13.     ) else set "group1=!group1! %%i"
  14. )
  15. echo group1:%group1%
  16. echo group2:%group2%
  17. pause
复制代码

作者: Batcher    时间: 2009-4-9 09:07

我觉得这个题目的描述可能有点问题,昨晚在你公布答案之前,我根本没有搞懂它到底是在问什么(也许是我理解能力有限)。
作者: AnyName    时间: 2009-4-9 18:54

新手,参考了2楼的部分代码
  1. @echo off&setlocal enabledelayedexpansion
  2. set /a sum=(1+12)*6
  3. set /a num=(!sum!/2/3-5)/2
  4. set /a num2=num+5
  5. for /l %%i in (!num!,1,!num2!) do (
  6.         set "gp1=!gp1! %%i"
  7.         set /a var=%%i+6
  8.         if !var! GTR 12 set /a var-=12
  9.         set "gp2=!gp2! !var!"
  10.         )
  11. echo group1:!gp1!
  12. echo group2:!gp2!
  13. endlocal
  14. pause
复制代码

[ 本帖最后由 AnyName 于 2009-4-9 18:59 编辑 ]
作者: BBCC    时间: 2009-4-9 19:32

将钟面分开然后将各部分数字相加?

暴力之~
作者: tireless    时间: 2009-4-10 11:32

  1. @echo off&setlocal enabledelayedexpansion
  2. for /l %%a in (1 1 12) do set /a All+=%%a
  3. for /l %%a in (1 1 12) do (
  4.   for /l %%i in (%%a 1 12) do (
  5.     for /l %%o in (%%a 1 %%i) do set /a Two+=%%o
  6.     set /a "1/(Two*2-All)" 2>nul && set "Two=" || call :End %%a %%i
  7.   )
  8. )
  9. :End
  10. for /l %%a in (1 1 12) do set "AB=!AB!%%a "
  11. for /l %%a in (%1 1 %2) do set "A=!A!%%a "
  12. echo %A%
  13. call echo %%AB:!A!=%%
  14. pause & exit
复制代码

[ 本帖最后由 tireless 于 2009-4-10 13:48 编辑 ]
作者: batman    时间: 2009-4-13 11:35

楼上6个for啊,是不是在效率上考虑欠妥了。。。
作者: batman    时间: 2009-4-13 12:27

在解本题时二楼和四楼都是使用的纯数学法,思路确是好的,但不是用批处理技巧来解
决的。小学三年级学生也根本想到以上所述的这两种方法,他们所用的方法就是一组一
组六个数字相加的方法,当然这用手工来做是个笨方法,但用批就不一样了,本人的代
码如下:
  1. @echo off&setlocal enabledelayedexpansion
  2. set "str=1 2 3 4 5 6 7 8 9 10 11 12"
  3. :lp
  4. for /f "tokens=1-6" %%a in ("%str%") do (
  5.     set /a num=%%a+%%b+%%c+%%d+%%e+%%f
  6.     if !num! equ 39 (
  7.        echo 第一组数为:%%a %%b %%c %%d %%e %%f
  8.        echo 第二组数为:!str:%%a %%b %%c %%d %%e %%f =!
  9.        pause>nul&goto :eof
  10.    ) else (
  11.        if %%a lss 10 (
  12.           set "str=%str:~2% %str:~,1%"
  13.           ) else (
  14.           set "str=%str:~3% %str:~,2%"
  15.        )
  16.        set /a num=0&goto lp
  17.    )
  18. )
复制代码

作者: tireless    时间: 2009-4-13 15:31

  1. @echo off
  2. set str=1 2 3 4 5 6 7 8 9 10 11 12
  3. call :a %str%
  4. pause & exit/b
  5. :a
  6. set /a six=0,six=%1+%2+%3+%4+%5+%6
  7. if %six% neq 39 shift & goto a
  8. echo %1 %2 %3 %4 %5 %6
  9. call echo %%str: %1 %2 %3 %4 %5 %6=%%
复制代码

作者: tyc    时间: 2009-4-14 17:55     标题: 我稳扎稳打的笨办法做出来的

  1. @echo off
  2. setlocal enabledelayedexpansion
  3. set /a half=(1+12)*6/2
  4. for /l %%i in (1,1,12) do (
  5. set /a a=%%i
  6. set  c=0
  7. set t1=
  8. for /l %%b in (1,1,6) do (
  9. set t1=!t1! !a!
  10. set /a c+=a
  11. set /a a+=1
  12. if !a! gtr 12 set /a a-=12
  13. )
  14. if !c! equ %half% echo !t1!
  15. )
  16. pause>nul
复制代码

作者: keen    时间: 2009-4-16 16:49

9楼的太帅了,加个分!
作者: Taurus    时间: 2010-1-2 11:53

9楼的真高,加分加分~~

在别forum看到此题,也把做好的贴到这里:
@echo off&setlocal enabledelayedexpansion
set var=1 2 3 4 5 6 7 8 9 10 11 12
:lp
for /f "tokens=1-12 delims= " %%a in ("%var%") do (
    set/a str1=%%a+%%b+%%c+%%d+%%e+%%f
    if "!str1!"=="39" set/p=%%a+%%b+%%c+%%d+%%e+%%f = %%g+%%h+%%i+%%j+%%k+%%l = !str1!&exit
)
for /f "tokens=1,* delims= " %%i in ("%var%") do set var=%%j %%i
goto :lp

[ 本帖最后由 Taurus 于 2010-1-2 12:15 编辑 ]
作者: qzwqzw    时间: 2010-1-2 15:02

另贴一组变态解法
充分体现简单问题复杂化的解题精神
其实按照小学生的解题思路
因为1-12中6,7两边的数加起来总是相等的
所以从6,7开始向两边数够3对数
也就是6,7,5,8,4,9
就可以满足解题条件了...
  1. @echo off
  2. echo.因为钟面所有数字由1-12的等差数列组成,
  3. echo.所以依据等差数列求和公式Sn=n(a1+an)/2 求得所有数字之和
  4. set /a S12=12*(1+12)/2
  5. echo.S12=12*(1+12)/2=%S12%
  6. echo.
  7. echo.因为两组数字之和相等,所以其中一组数字之和
  8. set /a S6=S12/2
  9. echo.S6=S12/2=%S6%
  10. echo.
  11. echo.因为每组数字共有6个,且必有一组为等差数列,
  12. echo.依据等差数列另一个求和公式Sn=na1+n(n-1)d/2 推得数列的起始数字
  13. set /a a1=(S6-6*(6-1)*1/2)/6
  14. echo.a1=(S6-6*(6-1)*1/2)/6=%a1%
  15. echo.
  16. echo.那么起始数字为a1的一组等差数列为:
  17. set /a a2=a1+1,a3=a1+2,a4=a1+3,a5=a1+4,a6=a1+5
  18. echo.%a1%,%a2%,%a3%,%a4%,%a5%,%a6%
  19. echo.
  20. echo.那么1-12中剩下的数字就是另外一组了
  21. set "num=1 2 3 4 5 6 7 8 9 10 11 12 "
  22. call echo.%%num:%a1% %a2% %a3% %a4% %a5% %a6% =%%
复制代码

作者: neorobin    时间: 2010-1-4 00:42

  1. ::我来做一个算术推理解法:
  2. ::假设分割线已找出, 在包含12点的一侧, 设其中的6个点按顺时针方向相邻分布分别为 g,h,i,j,k,l,  
  3. ::且其中顺时针方向在12后面的点都加上12, 即1点算作13点, 2点算作14点, 依此类推, 不含12点
  4. ::的一侧全按原数计算.  显然, g,h,i,j,k,l 都比它们各自关于钟心的对称点要大6, 所以这一侧的总和
  5. ::就比另一侧的总和大出 6*6=36, 按题目要求, 两侧的总和应相等, 这个大出的 36 就是由12点
  6. ::顺时针方向后面的点数都加了 12 造成的, 所以共有 36/12=3 个点加了12, 显然就是 1,2,3,
  7. ::所以分割线穿过3点和4点之间, 解毕.
  8. @echo off
  9. (set ps= 1 2 3 4 5 6 7 8 9 10 11 12) & (set /a "s=6*6/12+1, e=s+11")
  10. for /f "tokens=%s%-%e% delims= " %%a in ("%ps%%ps%") do echo %%a+%%b+%%c+%%d+%%e+%%f=%%g+%%h+%%i+%%j+%%k+%%l
  11. pause
复制代码

[ 本帖最后由 neorobin 于 2010-1-4 00:53 编辑 ]
作者: Taurus    时间: 2010-1-4 09:58

原帖由 neorobin 于 2010-1-4 00:42 发表
::我来做一个算术推理解法:
::假设分割线已找出, 在包含12点的一侧, 设其中的6个点按顺时针方向相邻分布分别为 g,h,i,j,k,l,  
::且其中顺时针方向在12后面的点都加上12, 即1点算作13点, 2点算作14点, 依此类推, 不 ...

这个真够简洁,一条算式完题了,一个loop也没有...
作者: qzwqzw    时间: 2010-1-5 11:24

扩展一下
任意一个n能被4整除的等差数列都可以平分
比如6,7,8,9,10,11,12,13
有兴趣的可以出一个通用解法
作者: a590687    时间: 2010-1-9 11:03

方法是 将表上所有数字之和除2  算出一半数字之和
再从1开始加6个数.如果和等于表上一半数字之和 就输出这6个数
  1. @echo off&setlocal enabledelayedexpansion
  2. for /l %%i in (1 1 12) do (
  3.     set /a a+=%%i
  4. )
  5. set /a n=%a%/2
  6. :lp
  7. for /l %%j in (1 1 6) do (
  8.     set /a b+=1
  9.     set c=!b!
  10.     for /l %%k in (1 1 6) do (
  11.         set /a c+=1
  12.         set /a d+=!c!
  13.         if !d! equ %n% (goto ak)
  14.     )
  15. )
  16. :ak
  17. set /a num=!b!+1
  18. echo. 应切分为:
  19. for /l %%l in (1 1 6) do (
  20. set /a num+=1
  21. echo !num!
  22. )
  23. pause
复制代码
  1. ::这是随机取值版本.比较费时间
  2. @echo off&setlocal enabledelayedexpansion
  3. set/a a=(1+12)*12/4/3
  4. :lp
  5. set/a b=%random%%%12+1
  6. set/a c=%random%%%12+1
  7. set/a d=%b%+%c%
  8. set/a e=%b%-%c%
  9. if %d% equ %a% (
  10.    if %e% equ 5 (goto end) else goto lp
  11. ) else goto lp
  12. :end
  13. echo.应切分为:
  14. set/p=!c!<nul
  15. for /l %%i in (1 1 5) do (
  16.     set/a f=%c%+%%i
  17.     set/p=!f!<nul
  18. )
  19. pause
复制代码
  1. ::这个是取差值版本
  2. @echo off&setlocal enabledelayedexpansion
  3. set/a a=(1+12)*12/4/3
  4. :lp
  5. for /l %%i in (1 1 12) do (
  6.     set/a b=%%i+5
  7.     set/a c=!b!+%%i
  8.     if !c! equ !a! (goto end)
  9. )
  10. :end
  11. echo.应切分为:
  12. echo !b!
  13. for /l %%j in (1 1 5) do (
  14.     set/a b-=1
  15.     echo !b!
  16. )
  17. pause
复制代码

[ 本帖最后由 a590687 于 2010-1-9 14:47 编辑 ]
作者: batman    时间: 2010-1-9 12:21

我再来一个:
  1. @echo off&setlocal enabledelayedexpansion
  2. set "str= #1 #2 #3 #4 #5 #6 #7 #8 #9 10 11 12 #1 #2 #3 #4 #5 #6 #7 #8 #9"
  3. for /l %%a in (1,1,7) do (
  4.     set /a "num=(2*%%a+5)*3"
  5.     if !num! equ 39 (
  6.        set /a "a=(%%a-1)*3",b="(%%a+5)*3"
  7.        call,set "a=%%str:~!a!,18%%"&echo !a:#=!
  8.        call,set "b=%%str:~!b!,18%%"&echo !b:#=!
  9.     )
  10. )
  11. pause>nul
复制代码

[ 本帖最后由 batman 于 2010-1-9 12:25 编辑 ]




欢迎光临 批处理之家 (http://www.bathome.net/) Powered by Discuz! 7.2