为什么Python没有像许多其他编程语言那样的'do while'循环,比如C?
示例:在C中我们执行while循环,如下所示:
do {
statement(s);
} while( condition );
Run Code Online (Sandbox Code Playgroud) 当我在大学(80年代中期)学习CS时,不断重复的一个想法是总是写出在顶部(而不是......)而不是在底部(做...同时)测试的循环.环.这些概念通常以对研究的参考作为后盾,这些研究表明,在顶部测试的循环在统计上比其底部测试对应物更可能是正确的.
结果,我几乎总是编写在顶部测试的循环.如果它在代码中引入了额外的复杂性,我不会这样做,但这种情况似乎很少见.我注意到一些程序员几乎专门编写在底部测试的循环.当我看到像这样的结构:
if (condition)
{
do
{
...
} while (same condition);
}
Run Code Online (Sandbox Code Playgroud)
或者反过来(if在里面while),它让我想知道他们是否真的以这种方式编写它,或者if当他们意识到循环没有处理null情况时他们添加了语句.
我做了一些谷歌搜索,但没有找到任何关于这个主题的文献.你们(和女孩们)如何写你的循环?
如何在C#中编写Do .. While循环?
(编辑:我是一名VB.NET程序员,试图转向C#,所以我确实有.NET/VB语法的经验.谢谢!)
这是我和老师之间长期争论的问题.能有一个地方的情况for循环绝对不能被代替的使用while/ do- while循环?换句话说,是否存在一个特定的情况,其中for-loop不能代替while循环; 是while/ do- while以任何方式"不同" for?
我有一个看起来像:
User user = userDao.Get(1);
do
{
// processing
// get the next user
//
user = UserDao.GetNext(user.Id);
if(user == null)
continue; // will this work?????????????
}
while ( user != null)
Run Code Online (Sandbox Code Playgroud)
如果它确实有效,它会转到do语句的顶部,而user是null,所以事情会破坏?
也许我应该将循环重写为while语句?
首先,我要说我同意goto语句在很大程度上与现代编程语言中的更高级别结构无关,并且在适当的替代品可用时不应使用.
我最近重新阅读了Steve McConnell的Code Complete原版,并忘记了他对常见编码问题的建议.几年前,当我第一次开始时,我已经读过它,并且不认为我意识到配方会有多么有用.编码问题如下:执行循环时,您经常需要执行循环的一部分来初始化状态,然后使用其他逻辑执行循环,并使用相同的初始化逻辑结束每个循环.一个具体的例子是实现String.Join(delimiter,array)方法.
我想每个人第一个接受这个问题的都是这个.假设定义了append方法以将参数添加到返回值.
bool isFirst = true;
foreach (var element in array)
{
if (!isFirst)
{
append(delimiter);
}
else
{
isFirst = false;
}
append(element);
}
Run Code Online (Sandbox Code Playgroud)
注意:稍微优化一下就是删除else并将其放在循环的末尾.赋值通常是单个指令并等效于else,并将基本块的数量减少1并增加主要部分的基本块大小.结果是在每个循环中执行一个条件以确定是否应该添加分隔符.
我也看到并使用了其他处理这个常见循环问题的方法.您可以先在循环外执行初始元素代码,然后从第二个元素到结尾执行循环.您还可以将逻辑更改为始终附加元素然后添加分隔符,一旦完成循环,您只需删除添加的最后一个分隔符.
后一种解决方案往往是我更喜欢的解决方案,因为它不会复制任何代码.如果初始化序列的逻辑发生变化,您不必记得在两个地方修复它.然而,它需要额外的"工作"来做某事然后撤消它,至少导致额外的cpu周期,并且在很多情况下,例如我们的String.Join示例也需要额外的内存.
我兴奋地阅读这个结构
var enumerator = array.GetEnumerator();
if (enumerator.MoveNext())
{
goto start;
do {
append(delimiter);
start:
append(enumerator.Current);
} while (enumerator.MoveNext());
}
Run Code Online (Sandbox Code Playgroud)
这样做的好处是,您没有重复的代码,也没有额外的工作.你开始循环进入第一个循环的执行的一半,那就是你的初始化.您只能使用do while构造模拟其他循环,但转换很容易并且阅读并不困难.
所以,现在问题.我很高兴尝试将其添加到我正在处理的一些代码中,发现它不起作用.在C,C++,Basic中工作得很好但是在C#中你不能跳转到不是父范围的不同词法范围内的标签.我很失望.所以我想知道,在C#中处理这个非常常见的编码问题(我主要在字符串生成中看到它)的最佳方法是什么?
或许更具体的要求:
我认为可读性是唯一可能因我说的配方而受到影响的事情.但它在C#中不起作用,那么下一个最好的东西是什么?
*编辑* 由于一些讨论,我改变了我的表现标准.性能通常不是限制因素,所以更正确的目标应该是不合理,不是最快的.
我不喜欢我建议的替代实现的原因是因为它们要么重复代码,这留下了改变一个部分而不是另一个部分的空间,或者对于我通常选择它的那个需要"撤消"操作,这需要额外的思考和时间来撤消事物你做的那件事.特别是对于字符串操作,这通常会让您因一个错误而打开,或者无法解释一个空数组并尝试撤消未发生的事情.
我们经常需要像这样的循环
do
{
Type value(GetCurrentValue());
Process(value);
}while(condition(value));
Run Code Online (Sandbox Code Playgroud)
不幸的是,这不会编译,因为value范围结束于}.这意味着我必须在循环之外声明它.
Type value;
do
{
value = GetCurrentValue();
Process(value);
}while(condition(value));
Run Code Online (Sandbox Code Playgroud)
至少有两个原因,我不喜欢这个.首先,我喜欢在当地宣布事物.第二,如果值不可赋值或默认可构造,则这是一个问题,但只能复制构造.
所以,我的问题有两个方面.首先,我想知道将do while的范围扩展到最终条件是否有特定的原因/困难(正如for循环中声明的变量的范围包括for循环的主体,尽管它实际上是在牙箍之外).如果你相信我的第一个问题的答案是"这就是它的方式.不要问为什么问题." 然后我想知道是否有成语可以帮助编写类似于我的例子中的do-while循环,但没有我提到的缺点.
希望问题清楚.
什么之间的区别尽管待办事项,其中语句在循环块中的第一行,只是单虽然在VB.NET?
他们似乎没有提供任何行为上的差异.
我有以下class两种方法的示例:
Process.java:
public class Process {
public Process() {
}
public static void countRecursive(int num) {
System.out.println("countRecursive: " + num++);
if (num <= 10) countRecursive(num);
else return;
}
public static void countWhile(int num) {
do System.out.println("countWhile: " + num++);
while (num <= 10);
}
}
Run Code Online (Sandbox Code Playgroud)
主要课程:
public static void main(String[] args) {
Process.countRecursive(0);
Process.countWhile(0);
}
Run Code Online (Sandbox Code Playgroud)
输出:
countRecursive: 0
countRecursive: 1
countRecursive: 2
countRecursive: 3
countRecursive: 4
countRecursive: 5
countRecursive: 6
countRecursive: 7
countRecursive: 8
countRecursive: 9
countRecursive: 10 …Run Code Online (Sandbox Code Playgroud) 我想为MySQL创建一个存储例程,用于计算一个月的业务或工作日数(工作日为周一至周五).
这是语法错误,但我不知道语法错误是什么.它告诉我的全部是:
1064 - 您的SQL语法出错; 查看与您的MySQL服务器版本对应的手册,以便在'WHILE(@ daycount <@totaldays)附近使用正确的语法DO IF(WEEKDAY(@checkweekday)<6)THEN'在第2行
我的语法错误如下:
WHILE(@daycount < @totaldays) DO
IF (WEEKDAY(@checkweekday) < 6) THEN
Run Code Online (Sandbox Code Playgroud)
我的代码:
SELECT MONTH(CURDATE()) INTO @curmonth;
SELECT MONTHNAME(CURDATE()) INTO @curmonthname;
SELECT DAY(LAST_DAY(CURDATE())) INTO @totaldays;
SELECT FIRST_DAY(CURDATE()) INTO @checkweekday;
SELECT DAY(@checkweekday) INTO @checkday;
SET @daycount = 0;
SET @workdays = 0;
BEGIN
WHILE(@daycount < @totaldays) DO
IF (WEEKDAY(@checkweekday) < 6) THEN
SET @workdays = @workdays+1;
END IF;
SET @daycount = @daycount+1;
SELECT ADDDATE('@checkweekday', INTERVAL 1 DAY) INTO @checkweekday;
END WHILE;
END;
SELECT @workdays; …Run Code Online (Sandbox Code Playgroud)