2013-02-22 41 views
31

Tôi đang cố gắng thực hiện một phép lọc trên một vectơ các cuộc tấn công, mỗi cuộc tấn công có ID duy nhất nói, 1-3.C++ cho mỗi phần, kéo từ các phần tử vector

Phương thức lớp học có đầu vào bàn phím từ 1-3.

Tôi đang cố gắng sử dụng một foreach để chạy qua các yếu tố của tôi trong m_attack để xem liệu số có phù hợp hay không, nếu có ... làm điều gì đó.

Vấn đề tôi đang nhìn thấy là thế này:

a'for each' statement cannot operate on an expression of type "std::vector<Attack 

Tôi đi về việc này hoàn toàn sai, tôi có C# kinh nghiệm và là loại gì tôi đang dựa trên, bất kỳ trợ giúp sẽ được đánh giá cao.

Mã của tôi là như sau:

Trong tiêu đề

vector<Attack> m_attack; 

Trong lớp

int Player::useAttack (int input) 
{ 

    for each (Attack* attack in m_attack) // Problem part 
    { 
     //Psuedo for following action 
     if (attack->m_num == input) 
     { 
      //For the found attack, do it's damage 
      attack->makeDamage(); 
     } 
    } 
} 
+2

Bạn có thể sử dụng hàm [std :: for_each] (http://www.cplusplus.com/reference/algorithm/for_each/) – andre

Trả lời

80

Ví dụ tiếp theo giả sử bạn sử dụng C++ 11. Ví dụ với tầm xa có trụ sở tại vòng:

for (auto &attack : m_attack) // access by reference to avoid copying 
{ 
    if (attack->m_num == input) 
    { 
     attack->makeDamage(); 
    } 
} 

Bạn nên sử dụng const auto &attack tùy thuộc vào hành vi của makeDamage().

Bạn có thể sử dụng std::for_each từ thư viện + lambdas tiêu chuẩn:

std::for_each(m_attack.begin(), m_attack.end(), 
     [](Attack * attack) 
     { 
      if (attack->m_num == input) 
      { 
       attack->makeDamage(); 
      } 
     } 
); 

Nếu bạn đang không thoải mái sử dụng std::for_each, bạn có thể vòng qua m_attack sử dụng vòng lặp:

for (auto attack = m_attack.begin(); attack != m_attack.end(); ++attack) 
{ 
    if (attack->m_num == input) 
    { 
     attack->makeDamage(); 
    } 
} 

Sử dụng m_attack.cbegin()m_attack.cend() để có được const vòng lặp.

+1

Ah, đó là tiêu đề tôi đã tìm kiếm sau đó, tôi đã săn tìm thư viện cho nó. Cảm ơn. – Springfox

+0

Thứ hai đó chỉ là những gì tôi đang thực sự quan tâm, và quan trọng hơn là tôi hiểu;). Cảm ơn vì điều đó, đã có nó. – Springfox

+0

@Justin Shrake: Có thể muốn giải thích lý do vượt qua bằng cách tham chiếu có lẽ là (nhưng không phải luôn luôn) thích hợp hơn trong phạm vi các vòng lặp, thay vì truyền bằng bản sao. – DavidO

16

Đây là cách nó sẽ được thực hiện trong một vòng lặp trong C++ (11):

for (const auto& attack : m_attack) 
    { 
     if (attack->m_num == input) 
     { 
      attack->makeDamage(); 
     } 
    } 

Không có for each bằng C++. Một tùy chọn khác là sử dụng std::for_each với hàm functor phù hợp (điều này có thể là bất kỳ thứ gì có thể được gọi với đối số Attack* làm đối số).

+0

['cho mỗi'] (http://blogs.msdn.com/ b/arich/archive/2004/09/08/227139.aspx) là một phần mở rộng được hỗ trợ trong bản gốc của VS C++ –

+0

+1 cho C++ 11 và tự động – sotrh

4

C++ không có tính năng vòng lặp for_each trong cú pháp của nó. Bạn phải sử dụng C++ 11 hoặc sử dụng chức năng mẫu std::for_each.

struct Function { 
    int input; 
    Function(int input): input(input) {} 
    void operator()(Attack& attack) { 
     if(attack->m_num == input) attack->makeDamage(); 
    } 
}; 
Function f(input); 
std::for_each(m_attack.begin(), m_attack.end(), f); 
+0

Đây là một trợ giúp như vậy, tôi gần như đã làm việc nhưng Tôi cần phải làm cho nó trở lại một int cho phương pháp này. Tôi đang cố gắng, tôi đã thử nhưng không thể tìm ra cách tham chiếu con trỏ ở vị trí chính xác khi trả lại, bạn có thể sửa câu trả lời của mình để trợ giúp không? – Springfox

+0

@Springfox Bạn có thể thêm các biến thành viên bổ sung vào cấu trúc nếu cần và truy cập chúng sau này bằng cách sử dụng f.method (...); – andre

+0

tại sao không std :: bắt đầu/std :: kết thúc trên m_attack? – paulm

4

Cú pháp for each được hỗ trợ dưới dạng phần mở rộng cho native C++ trong Visual Studio.

Ví dụ quy định tại msdn

#include <vector> 
#include <iostream> 

using namespace std; 

int main() 
{ 
    int total = 0; 

    vector<int> v(6); 
    v[0] = 10; v[1] = 20; v[2] = 30; 
    v[3] = 40; v[4] = 50; v[5] = 60; 

    for each(int i in v) { 
    total += i; 
    } 

    cout << total << endl; 
} 

(làm việc trong VS2013) không phải là cầm tay/chéo nền tảng nhưng cung cấp cho bạn một ý tưởng về làm thế nào để sử dụng for each.

Các lựa chọn thay thế tiêu chuẩn (được cung cấp trong phần còn lại của câu trả lời) áp dụng ở mọi nơi. Và tốt nhất là nên sử dụng chúng.

Các vấn đề liên quan