2013-08-18 69 views
11

Khi tôi lặp lại qua một số std::unordered_map với phạm vi dựa trên vòng lặp hai lần, thứ tự có được đảm bảo bằng nhau không?Có phải cho (auto i: unordered_map) được đảm bảo có cùng thứ tự mỗi lần không?

std::unordered_map<std::string, std::string> map; 

std::string query = "INSERT INTO table ("; 
bool first = true; 
for(auto i : map) 
{ 
    if(first) first = false; 
    else query += ", "; 
    query += i.first; 
} 
query += ") "; 

query += "VALUES ("; 
first = true; 
for(auto i : map) 
{ 
    if(first) first = false; 
    else query += ", "; 
    query += i.second; 
} 
query += ");" 

Trong ví dụ trên, chuỗi kết quả phải ở dạng đó. Do đó, điều quan trọng là cả hai lần, thứ tự lặp lại là như nhau.

INSERT INTO table (key1, key2, key3) VALUES (value1, value2, value3); 

Điều này có được đảm bảo bằng C++ không?

+0

Hãy cho tôi biết rằng bạn đang bảo vệ chống lại SQL injection ở đâu đó. –

+0

@ D.Shawley Tôi không vào lúc này. Nhưng đó là về tiết kiệm của một trò chơi máy tính. Tôi mã hóa trò chơi và không có cách nào để tiêm SQL từ bên ngoài mã ứng dụng cả. – danijar

+0

Tôi chỉ xoay quanh bất kỳ lúc nào mà tôi thấy xây dựng chuỗi SQL bằng chuỗi nối thô. –

Trả lời

19

Trình tự lặp lại của container kết hợp có thứ tự chỉ có thể thay đổi khi rehashing là kết quả của một hoạt động đột biến (như được mô tả trong C++ 11 23.2.5/8). Bạn không sửa đổi vùng chứa giữa các lần lặp, do đó, thứ tự sẽ không thay đổi.

Mặc dù đặc điểm kỹ thuật không tuyên bố rõ ràng rằng việc khôi phục không thể xảy ra bất kỳ lúc nào, làm như vậy sẽ làm mất hiệu lực tất cả các trình lặp trên vùng chứa, làm cho bất kỳ sự lặp lại nào là không thể.

17

Tại sao không xây dựng chúng lại với nhau?

for(auto i : map) 
{ 
    if(first) first = false; 
    else{ 
     keys += ", "; 
     query += ", "; 
    } 
    keys += i.first; 

    values += i.second; 
} 

std::string query = "INSERT INTO table (" + keys + ") VALUES (" + values ")"; 

Trông đẹp quá.

Xin lưu ý, nếu phần này là hiệu suất quan trọng, bạn có thể xem xét việc tối ưu hóa quá trình xây dựng chuỗi với std :: stringstream như here, mặc dù nó là not clear how much that might help

+1

Hãy xem xét sử dụng 'ostringstream' thay vào đó, nhưng đây là cách tiếp cận tốt hơn. –

+0

@ D.Shawley có thể nếu đây là một phần hiệu suất chuyên sâu. Khác này có thể là tốt hơn hoàn toàn trên cơ sở dễ đọc, hoặc là cách tôi chủ yếu tập trung vào việc sửa chữa vấn đề của mình. –

+0

Tuyệt vời! Tôi thậm chí có thể cắt giảm xuống, bởi vì chìa khóa đầu tiên và giá trị được đưa ra. 'std :: string keys =" id ", giá trị = to_string (Id); cho (auto i: serialized) keys + = "," + i.first, giá trị + = "," + i.second; '. – danijar