当前位置: 首页 > news >正文

【C++】泛型算法(五)泛型算法的使用与设计

一、使用泛型算法

头文件

#include<algorithm> 

常用泛型算法

  1. find()
    用于搜索无序集合中是否存在某值;
    搜索范围: iterator[first, last);
    如果搜索到目标,find() 会返回一个iterator指向该值,否则返回一个interator指向last。

  2. binary_search()
    用于有序集合的搜索;(效率比find()高
    如果搜索到目标就返回true,否则返回false。

  3. count()
    返回数值相符的元素数目。

  4. search()
    比对某个容器内是否存在某个子序列;
    例如给定序列{1,3,5,7,2,9},如果搜寻子序列{5,7,2},则search()会返回一个literator指向子序列起始处,如果子序列不存在,就返回一个iterator指向序列末尾。

  5. max_element()
    取得数列最大元素值;
    eg. max_element(vec.begin(), vec.end() );

  6. copy()
    eg. copy(vec.begin(), vec.end(), temp.begin() );
    前两个泛型指针标出复制范围,第三个指向复制行为的目的地(也是个容器)的第一个元素,后续元素会被依次填入;
    注意确保目标容器拥有足够的空间以放置每个即将到来的元素。

  7. sort()
    对新容器执行排序操作
    eg. sort( temp.begin(), temp.end() );

二、如何设计一个泛型算法

1. Function Object

  • 标准库预先定义好许多的function object,实现了我们原本可能以独立函数加以定义的事务;

  • function object是某种class的实例对象,对function call运算符重载,可使function object被当做一般函数来使用;

  • 目的:提高效率(运算符成为inline,从而消除“通过函数指针来调用函数”的过程)。

标准库function object:

  1. 六个算术运算:
  • plus< type >,
  • minus< type >,
  • negate< type >,
  • multiplies< type >,
  • divides< type >,
  • modules< type >
  1. 六个关系运算:
  • less< type >,
  • less_equal< type >,
  • greater< type >,
  • greater_equal< type >,
  • equal_to< type >,
  • not_equal_to< type>
  1. 三个逻辑运算:

分别对应:&&、||、!:

  • logical_and< type >,
  • logical_or< type >,
  • logical_not< type >

头文件:

#include <functional>;

举例一:

//sort()默认less-than即升序排列
//传入greater-than这个function object即降序排列
sort(vec.begin(), vec.end(), greater<int>());
//binary_search()默认less-than即升序排列
//为正确搜索vector,可调整排序如下:
binary_search(vec.begin(), vec.end(), elem, greater<int>() );

举例二:

//实现fib数列每个元素和自身相加、自身相乘、被加到对应的Pell数列
transform(
	fib.begin(), fib.end(), //(1)元素范围
	pell.begin(),           //(2)应用位置
	fib_plus_pell.begin(),  //(3)存放结果的位置
	plus<int>());			//(4)所应用的转换操作

2. Function Object Adapter

  • 适配器:对function object进行修改操作;
  • binder adapter将function object的参数绑定为某指定值(二元转化为一元)。

标准库binder adapter:

  1. bind1st 将指定值绑定第一个参数;
  2. bind2nd 将指定值绑定第二个参数。

举例

vector<int> filter(const vector<int> &vec, int val, less<int> &it)
{
	vector<int> nvec;
	vector<int>::const_iterator iter = vec.begin();

    //val绑定于less<int>的第二个参数上
    //于是每个less<int>都会与val比较
	while ( (iter = find_if(iter, vec.end(), bind2nd(it, val))) != vec.end() )
	{
	  //每当iter!=vec.end(),iter指向某个小于val的元素
		nvec.push_back(*iter);
		iter++;
	}
	return nvec;
}

泛型化比较

//non-template版本
vector<int> sub_vec( const vector<int> &vec, int val )
{
	vector<int> local_vec( vec );
	sort ( local_vec.begin(), local_vec.end() );
	
	vector<int>::iterator iter = 
		find_if (	local_vec.begin(),
					local_vec.end(),
					bind2nd( greater<int>(), val ));
	
	local_vec.erase ( iter, local_vec.end() );
	return local_vec;
}

//改为template
//更加泛型化
template <typename InputIterator,	typename OutputIterator,	typename ElemType, typename Comp>
OutputIterator
sub_vec ( InputIterator first, InputIterator last, OutputIterator at, const ElemType &val, typename Comp)
{
while ( (first = find_if(first, last, bind2nd(pred, val)  )) != last)  //not1(bind2nd(pred, val))可以一元取反,not2二元取反
	{
		//观察进行情况
		cout << "found value: " << *first << endl;

		*at = *first++;
	}
	return at;
}

总结

将最初的函数转化为泛型函数的呈现效果:
转化后的函数和元素类型无关、和比较操作无关、和容器类型无关,即可从消除函数和元素类型、容器类型、比较操作之间的关联入手,传入指针、进行元素类型和操作参数化等。

相关文章:

  • 使用scss简化媒体查询
  • 国家网络安全宣传周知识竞赛活动小程序界面分享
  • day44 数据库查询命令
  • SpringBoot3基础:最简项目示例
  • linux下文件操作命令
  • 工作比读研简单多了
  • cpolar内网穿透
  • 淘宝分布式文件存储系统( 二 ) -TFS
  • c++模板初阶
  • 行情分析——加密货币市场大盘走势
  • Tomcat多实例+Nginx动静分离、负载均衡
  • GDB 用法之参数输入
  • 全智V5+AXP233电源管理芯片调试
  • 年龄大了转嵌入式有机会吗?
  • canvas-绘图库fabric.js简介
  • 24.Xaml ListView控件-----显示数据
  • LabVIEW开发气动悬浮系统教学平台
  • python 第一次作业
  • 滚雪球学Java(24):Java反射
  • servlet中doGet方法无法读取body中的数据
  • 云南城投去年营收约19.29亿元,亏损4945万元
  • 新增1839个!2024年度本科专业备案和审批结果,公布
  • 男子为讨喜钱掰断劳斯莱斯小金人,警方:已介入处置
  • 都市文化·商业演剧·海派艺术:早期上海话剧商演发展新探索
  • 针对“二选一”,美团再次辟谣
  • 广西通报桂林、贵港、玉林三市应对不力:管不住山火和露天焚烧