Как я могу вернуть итератор для вектора уникальных указателей на объекты, используя строку для поиска объекта? - PullRequest
0 голосов
/ 09 июля 2019

У меня есть класс List, который содержит вектор с уникальными указателями на объекты ListItem.Я хотел бы создать функцию, которая возвращает итератор для конкретного ListItem.Сравнение будет выполнено с использованием строкового аргумента для сравнения с переменной имени строки ListItem.

Я безуспешно пытался использовать std :: find, find_if и т. Д.Когда я перебрал вектор, я не могу понять, как получить доступ к переменной name в объекте ListItem, чтобы сделать сравнение.

#include <iostream>
#include <vector>
#include <memory>
#include <string>
#include <iterator>
#include <algorithm>

class ListItem {
private:
    double quantity{ 0 };
    std::string weightUnit;
    std::string name;

public:
    ListItem(double quantity, std::string weightUnit, std::string name) : quantity{ quantity }, weightUnit{ weightUnit }, name{ name } {}
    ~ListItem() {}

    double getQuantity() { return quantity; }
    std::string getWeightUnit() { return weightUnit; }
    std::string getName() { return name; }

};

class List {
private:
    std::vector<std::unique_ptr<ListItem>>mylist;

public:
    std::vector<std::unique_ptr<ListItem>>::iterator search(std::string str) {
    /* This is where I'm stuck */

    }

    void removeListItem(std::string &name) {
        auto it = search(name);
        if (it != mylist.end()) {
            mylist.erase(it);
        }
    }

    void addListItem(double quantity, std::string weightUnit, std::string name) {

        mylist.push_back(std::make_unique<ListItem>(quantity, weightUnit, name));
    }

};



int main() {
    auto list = std::make_unique<List>();
    list->addListItem(2, "kg", "beef");
    list->addListItem(4, "lbs", "eggs");
    list->search("test");

}

1 Ответ

1 голос
/ 09 июля 2019

Вам необходимо захватить аргумент str в лямбда-выражении, который вы используете в качестве предиката.

   std::vector<std::unique_ptr<ListItem>>::iterator search(std::string str) {
        auto tester = [str](std::unique_ptr<ListItem>& li) { return li->getName() == str; };
        return std::find_if(mylist.begin(), mylist.end(), tester);
    }

Обратите внимание, что тип аргумента в лямбда-выражении будет unique_ptr<ListItem>.(В C ++ 14 вы могли бы просто использовать auto)

...