& 和 | 总是要计算两个操作数,将操作符两边的操作数按位与/或运算。
&& 和 || 先检查第一个操作数的值,再根据该值进行操作,可能根本就不处理第二个操作数,进行的是布尔运算。
在其他语言中也被叫做短路布尔表达式(Short-circult boolean expressions)。
x = (y != 0) && ( z / y > 5 );
如果y为0则会导致“除0错误”,所以可以先判断y的值,如果y为0则不会进行除法运算。
例:
/*
* The condition for this PT_WAIT_UNTIL is a little tricky: the
* protothread will wait here until all data has been acknowledged
* (data_acked() returns true) and until all data has been sent
* (send_data() returns true). The two functions data_acked() and
* send_data() must be called in succession to ensure that all
* data is sent. Therefore the & operator is used instead of the
* && operator, which would cause only the data_acked() function
* to be called when it returns false.
*/
PT_WAIT_UNTIL(&s->psockpt, data_acked(s) & send_data(s));
static char data_acked(register struct psock *s)
{
if(s->state == STATE_DATA_SENT && uip_acked()) {
if(s->sendlen > uip_mss()) {
s->sendlen -= uip_mss();
s->sendptr += uip_mss();
} else {
s->sendptr += s->sendlen;
s->sendlen = 0;
}
s->state = STATE_ACKED;
return 1;
}
return 0;
}
static char send_data(register struct psock *s)
{
if(s->state != STATE_DATA_SENT || uip_rexmit()) {
if(s->sendlen > uip_mss()) {
uip_send(s->sendptr, uip_mss());
} else {
uip_send(s->sendptr, s->sendlen);
}
s->state = STATE_DATA_SENT;
return 1;
}
return 0;
}
uip中 psock_send() 函数为了实现连续发送,需要每次检测上一次发送的是否收到了收到确认,并会发送数据(如果data_acked() 返回为false则为重发,否则发送下一段数据)。