16.12编写你自己版本的Blob和BlobPtr模板,包含书中未定义的多个const成员。

Blob.h(注意,成员函数的声明和定义要放在一个头文件中)

  1. /*记住,模板的头文件中通常既包括声明也包括定义。函数模板和类模板成员函数的定义通常放在头文件中,不能分开放。。。。谨记*/
  2. #ifndef BLOB_H
  3. #define BLOB_H
  4. #include<iostream>
  5. #include<vector>
  6. #include<string>
  7. #include<memory>
  8. #include<initializer_list>
  9. using namespace std;
  10. template <typename> class BlobPtr;
  11. template <typename> class Blob;
  12. template <typename T>
  13. bool operator==(const Blob<T>&,const Blob<T>&);
  14. template <typename T>
  15. class Blob
  16. {
  17. friend class BlobPtr<T>;
  18. friend bool operator==<T>
  19. (const Blob<T>&,const Blob<T>&);
  20. public:
  21. typedef T value_type;
  22. typedef typename vector<T>::size_type size_type;
  23. Blob();
  24. Blob(initializer_list<T> il);
  25. BlobPtr<T> begin() { return *this;}
  26. BlobPtr<T> end() { auto ret=BlobPtr<T>(*this,this->size()); return ret;}
  27. size_type size() const { return data->size();}
  28. bool empty() const { return data->empty();}
  29. void push_back(const T &t) { data->push_back(t);}
  30. void push_back(T &&t) { data->push_back(std::move(t));}
  31. void pop_back();
  32. T& front();
  33. T& back();
  34. const T& front() const;
  35. const T& back() const;
  36. T& operator[](size_type i);
  37. const T& operator[](size_type i) const;
  38. private:
  39. shared_ptr<vector<T>> data;
  40. void check(size_type i,const string &msg) const;
  41. };
  42. template <typename T>
  43. Blob<T>::Blob():
  44. data(std::make_shared<std::vector<T>>()) { }
  45.  
  46. template<typename T>
  47. Blob<T>::Blob(initializer_list<T> il):data(make_shared<vector<T>>(il)) {}
  48.  
  49. template<typename T>
  50. void Blob<T>::check(size_type i,const string &msg) const
  51. {
  52. if(i>=data->size())
  53. throw out_of_range(msg);
  54. }
  55.  
  56. template<typename T>
  57. void Blob<T>::pop_back()
  58. {
  59. check(,"pop_back");
  60. data->pop_back();
  61. }
  62.  
  63. template <typename T>
  64. T& Blob<T>::front()
  65. {
  66. check(,"front");
  67. return data->front();
  68. }
  69.  
  70. template<typename T>
  71. T& Blob<T>::back()
  72. {
  73. check(,"back");
  74. return data->back();
  75. }
  76.  
  77. template<typename T>
  78. const T& Blob<T>::front() const
  79. {
  80. check(,"front");
  81. return data->front();
  82. }
  83.  
  84. template<typename T>
  85. const T& Blob<T>::back() const
  86. {
  87. check(,"back");
  88. return data->back();
  89. }
  90. template<typename T>
  91. T& Blob<T>::operator[](size_type i)
  92. {
  93. check(i,"out_of_range");
  94. return (*data)[i];
  95. }
  96.  
  97. template<typename T>
  98. const T& Blob<T>::operator[](size_type i) const
  99. {
  100. check(i,"out_of_range");
  101. return (*data)[i];
  102. }
  103. template <typename T>
  104. bool operator==(const Blob<T> &lhs,const Blob<T> &rhs)
  105. {
  106. if(rhs.size()!=lhs.size())
  107. return false;
  108. for(size_t i=;i!=lhs.size();+i)
  109. if(lhs[i]!=rhs[i])
  110. return false;
  111. return true;
  112. }
  113.  
  114. template <typename T>
  115. ostream operator<<(ostream &os,const Blob<T> &a)
  116. {
  117. os<<"<";
  118. for(size_t i=;i!=a.size();++i)
  119. os<<a[i]<<" ";
  120. os<<">";
  121. return os;
  122. }
  123. template <typename T>
  124. bool operator==(const BlobPtr<T>&,const BlobPtr<T>&);
  125. template <typename T> class BlobPtr
  126. {
  127. friend bool operator==<T>
  128. (const BlobPtr<T>&,const BlobPtr<T>&);
  129. public:
  130. BlobPtr():curr(){}
  131. BlobPtr(Blob<T> &a,size_t sz=):wptr(a.data),curr(sz){}
  132. T& operator*() const
  133. {
  134. auto p=check(curr,"dereference past end");
  135. return (*p)[curr];
  136. }
  137. BlobPtr& operator++();
  138. BlobPtr& operator--();
  139. BlobPtr& operator++(int);
  140. BlobPtr& operator--(int);
  141. private:
  142. shared_ptr<vector<T>> check(size_t,const string &) const;
  143. weak_ptr<vector<T>> wptr;
  144. size_t curr;
  145. };
  146. template <typename T>
  147. shared_ptr<vector<T>> BlobPtr<T>::check(size_t i,const string &msg) const
  148. {
  149. auto ret=wptr.lock();
  150. if(!ret)
  151. throw runtime_error("unbind BlobPtr");
  152. if(i>=ret->size())
  153. throw out_of_range(msg);
  154. return ret;
  155. }
  156.  
  157. template <typename T>
  158. BlobPtr<T>& BlobPtr<T>::operator++()
  159. {
  160. check(curr,"++");
  161. ++curr;
  162. return *this;
  163. }
  164. template <typename T>
  165. BlobPtr<T>& BlobPtr<T>::operator--()
  166. {
  167. --curr;
  168. check(curr,"--");
  169. return *this;
  170. }
  171. template <typename T>
  172. BlobPtr<T>& BlobPtr<T>::operator++(int)
  173. {
  174. auto ret=*this;
  175. ++*this;
  176. return ret;
  177. }
  178.  
  179. template <typename T>
  180. BlobPtr<T>& BlobPtr<T>::operator--(int)
  181. {
  182. auto ret=*this;
  183. --*this;
  184. return ret;
  185. }
  186.  
  187. template <typename T>
  188. bool operator==(const BlobPtr<T> &lhs,const BlobPtr<T> &rhs)
  189. {
  190. return (lhs.wptr.lock().get()==rhs.wptr.lock().get())&&lhs.curr==rhs.curr;
  191. }
  192.  
  193. template <typename T>
  194. bool operator!=(const BlobPtr<T> &lhs,const BlobPtr<T> &rhs)
  195. {
  196. return !(rhs==lhs);
  197. }
  198.  
  199. #endif // BLOB_H

main.cpp

  1. #include "Blob.h"
  2.  
  3. int main()
  4. {
  5. Blob<string> b1; // empty Blob
  6. cout << b1.size() << endl;
  7. { // new scope
  8. Blob<string> b2 = {"a", "an", "the"};
  9. b1 = b2; // b1 and b2 share the same elements
  10. b2.push_back("about");
  11. cout << b1.size() << " " << b2.size() << endl;
  12. } // b2 is destroyed, but the elements it points to must not be destroyed
  13. cout << b1.size() << endl;
  14. for(auto p = b1.begin(); p != b1.end(); ++p)
  15. cout << *p << endl;
  16.  
  17. return ;
  18. }

16.14 编写Screen类模板,用非类型参数定义Screen的高和宽。

16.15为你的Screen模板实现输入和输出运算符。Screen类需要哪些友元来令输入和输出运算符正确工作。

  1. #include<iostream>
  2. #include <string>
  3. using namespace std;
  4. //模板非类型参数,友元一定要前置声明
  5. template <unsigned H,unsigned W>
  6. class Screen;
  7. template <unsigned H,unsigned W>
  8. ostream& operator<<(ostream &os,const Screen<H,W> &s);
  9. template <unsigned H,unsigned W>
  10. istream& operator>>(istream &is,Screen<H,W> &s);
  11. template <unsigned H,unsigned W>
  12. class Screen
  13. {
  14. friend ostream& operator<< <H,W> (ostream &os,const Screen<H,W> &s);
  15. friend istream& operator>> <H,W> (istream &is,Screen<H,W> &s);
  16. public:
  17. typedef string::size_type pos;
  18. Screen()=default;
  19. Screen(pos ht,pos wd,char c):height(ht),width(wd),contents(ht*wd,c){}
  20. char get() const
  21. {
  22. return contents[cursor];
  23. }
  24. inline char get(pos ht,pos wd) const;
  25. Screen &move(pos r,pos c);
  26. private:
  27. pos cursor=;
  28. pos height=H;
  29. pos width=W;
  30. string contents;
  31. };
  32.  
  33. template<unsigned H,unsigned W>
  34. char Screen<H,W>::get(pos ht,pos wd) const
  35. {
  36. pos row=ht*width;
  37. return contents[row+wd];
  38. }
  39.  
  40. template <unsigned H,unsigned W>
  41. Screen<H,W>& Screen<H,W>::move(pos r,pos c)
  42. {
  43. pos row=r*width;
  44. cursor=row+c;
  45. return *this;
  46. }
  47. template <unsigned H,unsigned W>
  48. ostream& operator<<(ostream &os,const Screen<H,W> &s)
  49. {
  50. os<<s.cursor<<" "<<s.height<<" "<<s.width<<" "<<s.contents[s.cursor]<<endl;
  51. return os;
  52. }
  53. template <unsigned H,unsigned W>
  54. istream& operator>>(istream &is,Screen<H,W> &s)
  55. {
  56. is>>s.cursor>>s.height>>s.width>>s.contents;
  57. return is;
  58. }
  59. int main()
  60. {}

16.16

模板类之间的友元关系实现Blob和BlobPtr的更多相关文章

  1. Hibernate中的Entity类之间的继承关系之一MappedSuperclass

    在hibernate中,Entity类可以继承Entity类或非Entity类.但是,关系数据库表之间不存在继承的关系.那么在Entity类之间的继承关系,在数据库表中如何表示呢? Hibernate ...

  2. 06 (OC)* iOS中UI类之间的继承关系

    iOS中UI类之间的继承关系 此图可以更好的让你去理解iOS中一些底层的关系.你能够了解以及理解UI类之间的继承关系,你会更加明白苹果有关于底层的东西,更有助于你的项目开发由它们的底层关系,就能更加容 ...

  3. JAVA类与类之间的全部关系简述+代码详解

    本文转自: https://blog.csdn.net/wq6ylg08/article/details/81092056类和类之间关系包括了 is a,has a, use a三种关系(1)is a ...

  4. Java类与类之间的继承关系

    Java父类与子类继承关系,调用的各种关系 示例一(子类调用父类函数): // 定义一类 A public class A { // 此方法打印一句话 public void a() { System ...

  5. Java学习笔记——I/O流常用类之间的继承关系及构造方法

    朝辞白帝彩云间,千里江陵一日还. 两岸猿声啼不住,轻舟已过万重山. ——早发白帝城 总结一下有哪些I/O流: 输入流方法主要是read()和close(),输出流方法主要是write().flush( ...

  6. VS2015 查看类之间的继承关系

    ---恢复内容开始--- 1. 右击项目名称,单击"查看"菜单下的"查看类图"菜单: 2.生成的类图如下:

  7. python_面向对象——类之间的依赖关系

    class Dog: def __init__(self,name,age,master): self.name = name self.age = age self.master = master ...

  8. 齐博X1模板页面之间的继承关系

    本节说明下模板页面间的继承 我们在前面建立了一个公共布局模板,并且利用{block name=xxx}...{/block}分割了三个部分区块 本节我们来看下模板之前的继承如何实现,首先我们建立一个i ...

  9. eclipse如何查看类之间的引用关系

    今天遇到这个问题:mark一点点: 在类名上单击右键.选择Reference->Workingspace快捷克债券Ctrl+Shift+G 版权声明:本文博客原创文章,博客,未经同意,不得转载.

随机推荐

  1. C语言可变参数在宏定义中的应用

    在C语言的标准库中,printf.scanf.sscanf.sprintf.sscanf这些标准库的输入输出函数,参数都是可变的.在调试程序时,我们可能希望定义一个参数可变的输出函数来记录日志,那么用 ...

  2. eclipse+maven搭建cxf webservice 完整例子

    开发环境是eclipse , maven. 在开发java webservice时,有两个比较流行的框架:axis2和cxf.cxf可以无缝的和spring集成,而axis2需要打包成aar文件,在t ...

  3. 使用VisualStudio2010创建C#应用程序

    打开VisualStudio2010,选择“文件”——“新建”——“项目”菜单命令.调出“新建项目”对话框.

  4. 李洪强iOS开发Swift篇—03_字符串和数据类型

    李洪强iOS开发Swift篇—03_字符串和数据类型 一.字符串 字符串是String类型的数据,用双引号""包住文字内容  let website = "http:// ...

  5. zip压缩解压缩 项目icsharpcode-SharpZipLib-e012155

    大家可以到http://www.icsharpcode.net/opensource/sharpziplib/ 下载SharpZiplib的最新版本,支持Zip, GZip, BZip2 和Tar格式 ...

  6. 【转】iOS开发:开发证书知识点总结

    原文网址:http://www.jianshu.com/p/9c166a5e4930 1. Error: An App ID with identifier "*" is not ...

  7. 【转】三十三、Android给ListView设置分割线Divider样式

    原文网址:http://www.cnblogs.com/linjiqin/archive/2011/11/12/2246349.html 给ListView设置分割线,只需设置如下两个属性: andr ...

  8. extjs form 取值 赋值 重置

    一.从form中获取field的三个方法: 1.Ext.getCmp('id'); 2.FormPanel.getForm().findField('id/name'); 3.Ext.get('id/ ...

  9. LoadRunner_Analysis(z) 分析

    LoadRunner_Analysis(z) 分析 lr_Analysis(z) Analysis Summary Page Analysis Summary(分析总结页面) 分为三个部分: Stat ...

  10. 算法 python实现(三) 快速排序

    算法学起来真费劲啊,智商只够捉只鸡的.昨晚没看明白就没电了,过两天要考虑偷电了... 今天看看快速排序,有一个博客写的很好,通俗生动形象,适合我这样的算法大白菜.推荐一下 http://www.cnb ...