26

规范对此主题的说明:

迭代循环具有以下形式:

IM IN YR <label> <operation> YR <variable> [TIL|WILE <expression>]  
  <code block>
IM OUTTA YR <label>

其中 <operation> 可以是 UPPIN(加一)、NERFIN(减一)或任何一元函数。该操作/函数应用于 <variable>,它是临时的,并且是循环的局部变量。TIL <expression> 将表达式计算为 TROOF:如果计算结果为 FAIL,则循环再次继续,否则,循环执行停止,并在匹配的 IM OUTTA YR <label> 之后继续。WILE <表达式> 是相反的:如果表达式是 WIN,则继续执行,否则循环退出。

问题

我对规范的抱怨是:

  • 缺少循环变量初始化器
  • 事实上它是循环的临时和本地的

据我了解,这意味着它必须从 0 开始。

虽然UPPIN对于NERFIN. 我在其他语言中最常见的递减循环变量的用法是“重复n次(n不重复使用)”习语和字符串操作,无论如何这在 LOLCODE 中都不是一个好主意。

是否有可能以一种比等效的循环或无操作形式的循环更简洁的方式NERFINn到 1 或 0 的循环减量?UPPIN

替代品比较

使用变体打印 5 4 3 2 1 UPPIN

IM IN YR LOOPZ UPPIN YR COWNTR TIL BOTH SAEM COWNTR AN 5
  VISIBLE DIFF OF 5 AN COWNTR
IM OUTTA YR LOOPZ

优点:简洁。
缺点:不能直接访问实际的循环变量。

使用无操作变体:

I HAS A COWNTR ITZ 5
IM IN YR LOOPZ
  VISIBLE COWNTR
  COWNTR R DIFF OF COWNTR AN 1
  BOTH SAEM COWNTR AN 0, O RLY?
  YA RLY, GTFO, OIC
IM OUTTA YR LOOPZ

优点:循环变量是直接可用的。
缺点:更长。

我能得到的最好的NERFIN

IM IN YR LOOPZ NERFIN YR COWNTR TIL BOTH SAEM COWNTR AN -5
  VISIBLE SUM OF 5 AN COWNTR
IM OUTTA YR LOOPZ

优点:错误...使用NERFIN
缺点:循环变量不能直接访问;比UPPIN变体可读性差(哈哈!);冗长没有好处。

TLDR 问题,重复

是否有可能以一种比等效的循环或无操作形式的循环更简洁的方式NERFINn到 1 或 0 的循环减量?UPPIN

我在语言规范级别 1.2使用lci 解释器。

4

1 回答 1

14

从 2007 年开始就有关于这个确切主题的设计讨论。当时的共识似乎建议添加一个FROM作为工作组希望快速进入 1.2 的解决方案:

http://forum.lolcode.com/viewtopic.php?pid=2484

该问题已提交并没有纳入 1.2 规范。但是,它显然在 1.3 规范中:

http://lolcode.com/proposals/1.3/loop2

不过,仍在进行中。我检查了一下,它还没有在存储库的“未来”分支中。我们可以通过查看循环解释器代码来看到这一点。截至 2011 年 8 月 24 日(在修订版 72c983d0667d4d650657e1b7c5f4c7054096b0dd 中)它仍然始终最初将循环变量 a 分配NUMBR为 0:

https://github.com/justinmeza/lci/blob/72c983d0667d4d650657e1b7c5f4c7054096b0dd/interpreter.c#L3434

然而,即使使用旧规范,理论上应该可以将 aTROOF与针对 -1 的测试结合使用,以允许从 5 倒数到 0 的相对干净的形式:

BTW countdown-test.lol
CAN HAS STDIO?
HAI 1.2

HOW DUZ I COUNTDOWN YR BOWNDZ
    I HAS A FIRSTIES
    FIRSTIES R WIN
    IM IN YR LOOPZ NERFIN YR COWNTR TIL BOTH SAEM COWNTR AN -1
        FIRSTIES
        O RLY?
            YA RLY
                COWNTR R BOWNDZ
                FIRSTIES R FAIL
        OIC

        VISIBLE COWNTR

    IM OUTTA YR LOOPZ
IF U SAY SO

COUNTDOWN 5

KTHXBYE

不幸的是,有一个“效率黑客”可以防止循环内的代码使用以下方法修改循环变量R

https://github.com/justinmeza/lci/blob/a6ef5811e8eb98935a16600b799bccbe4adffdde/interpreter.c#L3408

然而,由于这似乎是代码中的一个错误,而不是规范中的一个遗漏,它更有可能在 1.3 版本之前得到修复。打补丁interpreter.c使if (0 && stmt->update->type == ET_OP)代码countdown-test.lol按预期运行。如果您不必与未打补丁的安装共享代码,它可能是现有 1.2 LOLCODE 部署的合适临时解决方案。

于 2011-08-24T05:47:32.847 回答