SSD5_ Exercise 4分析
学习使用STL sort和find函数
list有两个版本的sort成员函数:
一个是不带参数的sort(),用来实现升序排列;
另一个是带参数的sort(greater<T> pr),用来实现降序排列。
Algorithms中的的Sort方法,也是我们这次实验的排序方法
下面的两参数的就是默认的排序,指定迭代器的初始与末尾
void sort( iterator start, iterator end );
三个参数的最后一个参数是bool类型的函数,用函数指定排序规则:如下所示
void sort( iterator start, iterator end, StrictWeakOrdering cmp );
bool cmp(int a,int b)
{
return a > b;
}
了解一下基本知识,看要求,背景就不用管了
This assessment extends the Auction project to sort and filter by keyword the advertised items. A user of the system will have the ability to sort by the seller email address, the posting date, the closing date, and the quantity of items.
To complete this exercise, add sorting and filtering support to class Listing.
我找到Exercise2的实验结果并对比Listing.h
Listing.h
#ifndef LISTING_H #define LISTING_H #include <iostream> #include <vector> #include <iterator> #include <algorithm> #include <functional> #include "Advertisement.h" using namespace std; class Listing; class Listing { protected: typedef vector<Advertisement*> Container; public: typedef Container::iterator iterator; protected: Container objects; public: virtual ~Listing() {}; virtual Advertisement* operator[](const int& number); virtual void add(Advertisement* ptr); virtual iterator begin(); virtual iterator end(); // return a sorted copy of this Listing virtual Listing sort(string field); // return a filtered by keyword copy of this Listing virtual Listing filter(string keyword); }; #endif
Listing.cpp
#include "Listing.h" #include <algorithm> #include <functional> using namespace std; /* * This returns the Advertisement pointer whose number equals the parameter number. * Note, this is not the same as returning the pointer that exists and at index number. */ Advertisement* Listing::operator[](const int& number) { Listing::iterator it; for (it = this->begin(); it != this->end(); it++) { if ((*it)->getNumber() == number) { return *it; } } return NULL; } //Adds the Advertisement pointer given by the parameter to the vector objects. void Listing::add(Advertisement* ptr) { objects.push_back (ptr); } //This returns an iterator to the first Advertisement* in vector objects Listing::iterator Listing::begin() { return objects.begin(); } //This returns an iterator to the last Advertisement* in vector objects. Listing::iterator Listing::end() { return objects.end(); }
然后按照题目要求在里面补充两个方法即可
Changes to class Listing will allow a user of class Listing to sort advertisements and filter advertisements based on a keyword. To support these new requirements, class Listing has been modified to add methods sort and filter.
- virtual Listing sort(string field);
This is a new method. This method returns a copy of the invoking Listing object sorted by the field name given in the parameter. Use an appropriate STL sorting function to sort the advertisements. To sort based on the field name given by the parameter field, consider using an STL sort function that uses a predicate to determine object equality. The field names that can be passed into this function are "email," "start," "close," and "quantity."
- virtual Listing filter(string keyword);
This is a new method. This method a new instance of a Listing object that contains only those advertisements whose name or description contains the string given by the parameter keyword. If the parameter keyword equals the empty string (""), return a copy of the invoking Listing object. Use STL functions where appropriate. Some STL functions to consider are copy, remove_if, for_each, and find. The member function find of class string should be considered as well. Regardless of the STL functions used, a solution should not use any for-loops or while-loops.
直接上代码
Listing.cpp
//引入三个头文件 #include "Listing.h" //排序规则 #include "SortBy.h" //过滤规则 #include "CopyByKeyword.h" #include <algorithm> #include <functional> /* * 作者:白强 */ using namespace std; Advertisement* Listing::operator[](const int& number) { Listing::iterator it; for (it = this->begin(); it != this->end(); it++) { if ((*it)->getNumber() == number) { return *it; } } return NULL; } //Adds the Advertisement pointer given by the parameter to the vector objects. void Listing::add(Advertisement* ptr) { objects.push_back (ptr); } //This returns an iterator to the first Advertisement* in vector objects Listing::iterator Listing::begin() { return objects.begin(); } //This returns an iterator to the last Advertisement* in vector objects. Listing::iterator Listing::end() { return objects.end(); } //新增加的sort方法 Listing Listing::sort(string field) { //拷贝构造函数 Listing listing(*this); //排序方法,第三个参数是比较规则 std::sort(listing.begin(), listing.end(), SortBy(field)); return listing; } //过滤方法 Listing Listing::filter(string keyword) { //构造一个Listing对象 Listing listing; //构造CopyByKeyword对象 CopyByKeyword cp(keyword, &listing); //Regardless of the STL functions used, a solution should not use any for-loops or while-loops. for_each(this->begin(), this->end(), cp); return listing; }
附上两个规则文件
SortBy.h
#ifndef SORTBY_H #define SORTBY_H #include <string> #include "Advertisement.h" using namespace std; class SortBy { private: string keyField; public: //参数初始化keyField SortBy::SortBy(string keyField) : keyField(keyField) {} bool SortBy::operator()(Advertisement *a1, Advertisement *a2) { //根据keyField来比较 if (keyField == "email") { return (a1->getEmail() < a2->getEmail()); } if (keyField == "start") { return (a1->getStart() < a2->getStart()); } if (keyField == "close") { return (a1->getClose() < a2->getClose()); } if (keyField == "quantity") { return (a1->getQuantity() < a2->getQuantity()); } return false; } }; #endif
CopyByKeyword.h
#ifndef COPYBYKEYWORD_H #define COPYBYKEYWORD_H #include <string> #include "Advertisement.h" #include "Listing.h" using namespace std; class CopyByKeyword { private: string keyword; Listing* listing; public: //初始化 CopyByKeyword::CopyByKeyword(string keyword, Listing* listing) :keyword(keyword), listing(listing) {} void CopyByKeyword::operator()(Advertisement *ad) const { //调用find方法找到就加入listing,不要忘记题目要求 /* This is a new method. This method a new instance of a Listing object that contains only those advertisements whose name or description contains the string given by the parameter keyword. If the parameter keyword equals the empty string (""), return a copy of the invoking Listing object. */ //static const size_type npos = static_cast<size_type>(-1); if (string::npos != ad->getTitle().find(keyword) ||string::npos != ad->getBody().find(keyword) || keyword == "") { listing->add(ad); } } }; #endif
题目到这里就完了,至于能不能运行,就看造化了
我觉得还是学习这些核心的函数有意义,比如find与sort函数用法
下期再谈