问题的引出
在计算机程序中,除了常见的执行流程控制,还有逻辑流程控制;有时,执行流程即为逻辑流程,但在大多数情况下还是有所区别的,例如,假定有一个Web服务器使用同步套接字读取HTTP请求,那么会编写如下的代码:
void read(HTTP_REQUEST& http_request) { read(http_request.header); read(http_request.body, http_request.header); }
void read(HTTP_REQUEST_HEADER& header) { string line = read_line(); parse_request_link(line, header.method, header.uri, header.version);
while (TRUE) { line = read_line(); if (line.empty()) break;
parse_header_field(line, header); } }
void read(BYTE[]& body, HTTP_REQUEST_HEADER& header) { string transfer_encoding = header.fields['Transfer-Encoding']; if (transfer_encoding != b.chunkedb.) body = read_bytes(header.fields['Content-Length']); else { while (TRUE) { string chunk_header = read_line(); DWORD chunk_size = atoi(chunk_header); if (chunk_size == 0) break; BYTE[] chunk_body = read_bytes(chunk_size); body += chunk_body; } } }
string read_line() { while (TRUE) { int n = strpos(read_buffer, b./nb., read_buffer.size()); if (n > 0) break; read_buffer += socket.read(); } return read_buffer.extract(n); }
Byte[] read_bytes(int sz) { while (TRUE) { if (sz <= read_buffer.size()) break; read_buffer += socket.read(); } return read_buffer.extract(sz); } |
在这段代码中,执行流程与逻辑流程是一致的,然而,如果在那些被动接收事件的场合使用了异步套接字,就必须编写下面这样的代码了:
read() { read_buffer += socket.read(); if (state == read_request_line) { if (!read_line(line)) return; parse_request_link(line, method, uri, version); state = read_header_field; } while (state == read_request_line) { if (!read_line(line)) return; if (line.empty()) { transfer_encoding = header.fields['Transfer-Encoding']; if (transfer_encoding != b.chunkedb.) { content_length = header.fields['Content-Length']; state = read_body; } else state = read_chunk_header; } else parse_header_field(line, header, value); } if (state == read_body) { request_body += read_buffer; read_buffer.clear(); if (request_body.size() >= content_length) state = read_finished; return; } if (state == read_chunk_header) { if (!read_line(line)) return; chunk_size = atoi(line); if (chunk_size == 0) { state = read_finished; return; } state = read_body; } if (state == read_chunk_body) { request_body.append(read_buffer, chunk_size); if (chunk_size == 0) state = read_chunk_header; return; } } |
执行流程完全不同了,但逻辑流程却仍保持不变,因为只能一块一块地接收数据,还必须保存状态值及其他变量,以便在事件发生时进行相应的处理。以上只是一些示范性代码,并不能真正工作,在实际中要编写像这样的函数会更加复杂,也更加容易出错。 <  
1/2 1 2 下一页 尾页 |