当前位置: 首页 > 知识库问答 >
问题:

C/C中的无限循环[闭合]

爱博达
2023-03-14

进行无止境循环有多种可能性,我会选择以下几种:

  • for(;;) {}
  • 而(1){}/而(true){}
  • do{}而(1)/do{}而(true)

是否有某种形式可以选择?现代编译器是在中间语句和最后一个语句之间做出了区别,还是意识到这是一个无止境的循环,完全跳过了检查部分?

编辑:正如前面提到的,我忘记了goto,但这样做的原因是我根本不喜欢它作为一个命令。

共有3个答案

谢和同
2023-03-14
匿名用户

在一个极度无聊的行为中,我实际上编写了这些循环的几个版本,并在我的MacMini上用GCC进行编译。

同时(1){}和(;;) {}产生了相同的汇编结果,而do{}同时(1);产生了相似但不同的汇编代码

这是一个while/for循环

    .section    __TEXT,__text,regular,pure_instructions
    .globl  _main
    .align  4, 0x90
_main:                                  ## @main
    .cfi_startproc
## BB#0:
    pushq   %rbp
Ltmp2:
    .cfi_def_cfa_offset 16
Ltmp3:
    .cfi_offset %rbp, -16
    movq    %rsp, %rbp
Ltmp4:
    .cfi_def_cfa_register %rbp
    movl    $0, -4(%rbp)
LBB0_1:                                 ## =>This Inner Loop Header: Depth=1
    jmp LBB0_1
    .cfi_endproc

和do time循环

        .section    __TEXT,__text,regular,pure_instructions
    .globl  _main
    .align  4, 0x90
_main:                                  ## @main
    .cfi_startproc
## BB#0:
    pushq   %rbp
Ltmp2:
    .cfi_def_cfa_offset 16
Ltmp3:
    .cfi_offset %rbp, -16
    movq    %rsp, %rbp
Ltmp4:
    .cfi_def_cfa_register %rbp
    movl    $0, -4(%rbp)
LBB0_1:                                 ## =>This Inner Loop Header: Depth=1
    jmp LBB0_2
LBB0_2:                                 ##   in Loop: Header=BB0_1 Depth=1
    movb    $1, %al
    testb   $1, %al
    jne LBB0_1
    jmp LBB0_3
LBB0_3:
    movl    $0, %eax
    popq    %rbp
    ret
    .cfi_endproc

钱均
2023-03-14
匿名用户

这是非常主观的。我这样写:

while(true) {} //in C++

因为它的意图非常清晰,也很可读:你看了它,你就知道无限循环是有意的。

可以说for(;;)也很清楚。但我认为,由于其错综复杂的语法,这个选项需要额外的知识才能得出结论,即它是一个无限循环,因此相对不太清楚。我甚至会说,有更多的程序员不知道for(;;)做什么(即使他们知道循环的常规),但是几乎所有知道循环的程序员都会立即弄清楚而(true)可以。

对我来说,为(;)写表示无限循环,就像编写while()表示无限循环——前者有效,后者无效。在前一种情况下,空条件隐式地变成true,但在后一种情况下,它是一个错误!我个人不喜欢它。

现在,而(1)也参加了比赛。我想问:为什么而(1)?为什么不while(2)while(3)while(0.1)?好吧,不管你写什么,你实际上是指,而(true)——如果是这样,为什么不改写呢?

在C语言中(如果我写的话),我可能会这样写:

while(1) {} //in C

While(2)While(3)While(0.1)同样有意义。但是为了与其他C程序员保持一致,我会在(1)时编写,因为很多C程序员都编写了这个,我没有理由偏离规范。

万承志
2023-03-14

问这个问题的问题是,你会得到很多主观的答案,只是简单地说“我更喜欢这个…”。我将尝试用事实和参考来回答这个问题,而不是用个人观点来回答,而不是做这样毫无意义的陈述。

根据经验,我们可以从排除do-time替代方法(和goto)开始,因为它们不常用。我不记得曾经在专业人员编写的实时生产代码中见过它们。

while(1)while(true)和(;;)的是真实代码中常见的3个不同版本。当然,它们是完全等效的,并产生相同的机器代码。

(;;)的

>

  • 这是永恒循环的原始规范示例。在Kernighan和Ritchie的古代C圣经C编程语言中,我们可以读到:

    K

    for (;;) {
    ...
    }
    

    是一个“无限”循环,可能会被其他方式打破,例如中断或返回。使用while还是for在很大程度上取决于个人偏好。

    很长一段时间(但不是永远),这本书被认为是正典和C语言的定义。自从K

    然而,K

    今天,K

    但是尽管K

    反对(;;)的的参数 循环是因为它有点模糊和不可读。要了解代码的功能,您必须了解标准中的以下规则:

    ISO 9899:20116.8.5.3:

    for ( clause-1 ; expression-2 ; expression-3 ) statement
    

    /--/

    从句-1和表达式-3都可以省略。省略的表达式-2被非零常量替换。

    基于标准中的这段文字,我想大多数人会同意它不仅模糊,而且微妙,因为for循环的第一和第三部分与第二部分被省略时的处理方式不同。

    while(1)

    >

  • 对于(;;)来说,这应该是比更可读的形式 。然而,它依赖于另一条模糊但众所周知的规则,即C将所有非零表达式视为布尔逻辑true。每个C程序员都知道这一点,所以这不太可能是个大问题。

    这种形式有一个很大的实际问题,即编译器倾向于给它一个警告:“条件始终为真”或类似的警告。这是一个很好的警告,您确实不想禁用它,因为它对于查找各种bug非常有用。例如,当程序员打算编写while(i=1)时,出现了一个bug,例如while(i=1)

    此外,外部静态代码分析器可能会抱怨“条件总是真实的”。

    while(true)

    >

  • 为了使while(1)更具可读性,有些人使用while(true)。程序员之间的共识似乎是,这是最可读的形式。

    然而,这种形式具有与同时(1)相同的问题,如上所述:条件总是true警告。

    当涉及到C时,这种形式还有另一个缺点,即它使用stdbool. h中的宏true。因此,为了进行编译,我们需要包含一个头文件,这可能不方便,也可能不方便。在C语言中,这不是一个问题,因为bool作为一个基本数据类型存在,而true是一个语言关键字。

    这种形式的另一个缺点是它使用C99 bool类型,这只在现代编译器上可用,不能向后兼容。同样,这只是C语言中的问题,而不是C语言中的问题。

    那么使用哪种形式呢?两者似乎都不完美。是的,正如K

    就我个人而言,我总是对(;)使用 只是为了避免其他表单频繁生成的编译器/分析器警告。但也许更重要的是,正因为如此:

    如果即使是C初学者也知道for(;;)意味着一个永恒的循环,那么你想让代码对谁来说更可读呢?

    我想这就是一切真正的原因。如果您发现自己试图让非程序员(他们甚至不知道编程语言的基本部分)能够读懂源代码,那么您只是在浪费时间。他们不应该阅读你的代码。

    既然每个应该阅读你的代码的人都知道(;)的 的意思是,没有必要让它更具可读性——它已经是可读性了。

  •  类似资料:
    • 这是一个类的简单程序,它以分钟为单位提示用户他或她淋浴的时间长度(作为正整数,根据需要重新提示),然后打印同等数量的水瓶(作为整数)。 假设淋浴器每分钟使用1.5加仑水(192盎司),塑料瓶大小为16盎司 我的do-while循环成功地拒绝了负数和0,但是,如果我输入“foo”这样的文本,当提示输入淋浴的长度(以分钟为单位)时,程序将进入无限循环,永远运行该循环并打印“How long is yo

    • 本文向大家介绍C和C ++中的循环,包括了C和C ++中的循环的使用技巧和注意事项,需要的朋友参考一下 在本教程中,我们将讨论一个程序,以了解C和C ++中的循环。 当我们不得不一次又一次地执行给定的块代码时,使用编程中的循环。它采用了一次又一次编写同一代码行的方法,并促进了DRY代码实践。 示例 对于循环 输出结果 While循环 输出结果

    • 我正在尝试编写一个线程,该线程将在我的主程序的后台运行,并监视某些内容。在某个时候,主程序应该向线程发出安全退出的信号。下面是一个以固定间隔将本地时间写入命令行的最小示例。 当“on”变量没有通过引用传递时,此代码会编译并产生预期的结果,只是线程永远不会终止。一旦变量通过引用传递,我就会收到编译器错误 您能建议一种修复此代码的方法吗? 额外的问题:哪里出了问题,为什么它可以与std::ref一起工

    • 我有一个循环,不断从我的串行端口读取。循环是无限的,所以我所知道的停止程序的唯一方法是使用。这个解决方案的问题是,当我使用时,我的程序会突然结束,我怀疑这也会导致其他问题。在程序结束时,我关闭了与我正在访问的串行端口的文件描述符的连接,但是我认为我的程序从来没有达到这个连接,因为我使用了命令,它只是在正确的位置停止程序它是。 有没有一种方法可以让我创建无限的time循环,并在我想要的时候退出,但同

    • 本文向大家介绍Objective-C实现无限循环轮播器,包括了Objective-C实现无限循环轮播器的使用技巧和注意事项,需要的朋友参考一下 先看看效果图: 具体实现代码: 1. 控制器     2. 显示内容界面设置 以上就是本文的全部内容,希望对大家的学习有所帮助。

    • 有的时候,可能需要多次执行同一块代码。一般情况下,语句是顺序执行的:函数中的第一个语句先执行,接着是第二个语句,依此类推。 编程语言提供了允许更为复杂的执行路径的多种控制结构。 循环语句允许我们多次执行一个语句或语句组,下面是大多数编程语言中循环语句的一般形式: 循环类型 C++ 编程语言提供了以下几种循环类型。点击链接查看每个类型的细节。 循环类型 描述 while 循环 当给定条件为真时,重复