一个课堂打印案例分析_C/C++语言_黑客防线网安服务器维护基地--Powered by WWW.RONGSEN.COM.CN

一个课堂打印案例分析

作者:黑客防线网安C/C++教程基地 来源:黑客防线网安C/C++教程基地 浏览次数:0

本篇关键词:打印课堂一个 
黑客防线网安网讯:     本章讲的是一个简单的打印案例,完全可用几行代码来完成,而面对问题不断复杂化,我们发现修改过程式的代码不足以支撑需求的多变。  作者构造了Picture类,汇总需求细节,见招拆招,...
     本章讲的是一个简单的打印案例完全可用几行代码来完成而面对问题不断复杂化,我们发现修改过程式的代码不足以支撑需求的多变
  作者构造了Picture类,汇总需求细节,见招拆招,尤其在“接口设计”这一节里,把自己当成客户,跟自己一问一答(“我希望有些什么操作,如何表述这些操作?”),逐步分析不断复杂的需求,然后抽象出接口,其中不乏作者的经验之谈:要想决定具体操作的形式,有一个好办法,就是试着使用这些操作,从使用的例子推导出操作的定义形式要比从头苦思冥想地发明这些操作容易得多
  1、最初需求是打印如下文字:
  Paris
  in the
  Spring
  2、构造的Picture类,只需要一个构造函数和一个输出即可完成,如果打印如下文字:
  +-------+
  |Paris  |
  |in the |
  |Spring|
  +-------+
  3、如果使用C式的过程代码,需要做些打印内容的改变可以完成,作者为Picture类添加了一个frame(Picture&)来完成,如果打印内容改变了,我想C式代码作者就会抓头皮了:
  Paris  +-------+
  in the |Paris  |
  Spring|in the |
  |Spring|
  +-------+
  4、Picture类便有了 Picture operator |(const Picture&, const Picture&) 接口,用字符‘|’做两个Picture对象的横向合并,用Picture operator &(const Picture&,const Picture&)接口,用字符‘&’做纵向合并,当我们需要打印如下文字的时候:
  +--------------+
  |+------+      |
  ||Paris |      |
  ||in the|      |
  ||Spring|      |
  |+------+      |
  |Paris +------+|
  |in the|Paris ||
  |Spring|in the||
  |      |Spring||
  |      +------+|
  +--------------+
  我们只需要一句 cout << frame(frame(p) & (p | frame(p))) << endl即可完成。
  下面是Picture类的源码(原书代码中有些许错误,均做过修改和测试):
  1 #include <iostream>
  2
  3
  4  using namespace std;
  5
  6  class Picture
  7 {
  8     friend Picture frame(const Picture&);                      //加框
  9      friend Picture operator&(const Picture&, const Picture&);  //纵向合并
  10      friend Picture operator|(const Picture&, const Picture&);  //横向合并
  11      friend ostream& operator << (ostream& o, const Picture& p);
  12  private:
  13     int height, width;
  14     char* data;
  15     char& position(int row, int col){
  16         return data[row * width + col];
  17     };
  18     char position(int row, int col) const{
  19         return data[row * width + col];
  20     };
  21     void copyblock(int,int,const Picture&);
  22 public:
  23     Picture() : height(0),width(0),data(0){};
  24     Picture(const char* const*, int);
  25     Picture(const Picture& );
  26     ~Picture();
  27     Picture& operator=(const Picture&);
  28     static int max(int m, int n)
  29     {
  30         return m > n ? m : n;
  31     };
  32     void init(int h, int w);
  33     void clear(int , int ,int ,int );
  34 };
  35
  36 ostream&
  37 operator << (ostream& o, const Picture& p)
  38 {
  39     for(int i = 0; i < p.height; ++i)
  40     {
  41         for(int j =0; j < p.width; ++j)
  42             o << p.position(i,j);
  43         o << endl;
  44     }
  45     return o;
  46 };
  47
  48
  49 void Picture::init(int h, int w)
  50 {
  51     height = h;
  52     width = w;
  53     data = new char[height * width];
  54 };
  55
  56 Picture::Picture(const char* const* array, int n)
  57 {
  58     int w = 0;
  59     int i ;
  60     for(i = 0; i < n; i++)
  61         w = Picture::max(w, strlen(array[i]));
  62     init(n,w);
  63     for(i = 0; i < n; i++)
  64     {
  65         const char* src = array[i];
  66         int len = strlen(src);
  67         int j = 0;
  68         while(j < len)
  69         {
  70             position(i,j) = src[j];
  71             ++j;
  72         }
  73         while(j < width)
  74         {
  75             position(i, j) = ' ';
  76             ++j;
  77         }
  78     }
  79 }
  80
  81 Picture::Picture(const Picture& p):
  82          height(p.height), width(p.width),
  83          data(new char[p.height * p.width])
  84 {
  85     copyblock(0,0,p);
  86 }
  87
  88 Picture::~Picture()
  89 {
  90     delete []data;
  91 }
  92
  93 Picture& Picture::operator=(const Picture& p)
  94 {
  95     if(this != &p)
  96     {
  97         delete []data;
  98         init(p.height,p.width);
  99         copyblock(0,0,p);
  100     }
  101     return *this;
  102 }
  103
  104 void Picture::copyblock(int row,int col,const Picture& p)
  105 {
  106     for(int i =0; i < p.height; ++i)
  107     {
  108         for(int j =0; j < p.width; ++j)
  109             position(i+row, j+col) = p.position(i,j);
  110     }
  111 }
  112
  113 void Picture::clear(int h1,int w1,int h2,int w2)
  114 {
  115     for(int r = h1; r < h2; ++r)
  116         for(int c = w1; c < w2; ++c)
  117             position(r,c) = ' ';
  118 }
  119
  120 Picture frame(const Picture& p)
  121 {
  122     Picture r;
  123     r.init(p.height + 2, p.width + 2);
  124     for(int i = 1; i < r.height -1; ++i)
  125     {
  126         r.position(i,0) = '|';
  127         r.position(i, r.width - 1) = '|';
  128     }
  129     for(int j = 1; j < r.width - 1; ++j)
  130     {
  131         r.position(0, j) = '-';
  132         r.position(r.height - 1, j) = '-';
  133     }
  134     r.position(0, 0) = '+';
  135     r.position(0, r.width-1) = '+';
  136     r.position(r.height-1, 0)= '+';
  137     r.position(r.height-1,r.width-1)='+';
  138     r.copyblock(1,1,p);
  139     return r;
  140 }
  141
  142 Picture operator&(const Picture& p, const Picture& q)
  143 {
  144     Picture r;
  145     r.init(p.height + q.height, Picture::max(p.width ,q.width));
  146     r.clear(0,p.width,p.height,r.width);
  147     r.clear(p.height,q.width,r.height,r.width);
  148     r.copyblock(0,0,p);
  149     r.copyblock(p.height,0,q);
  150     return r;
  151 }
  152
  153 Picture operator|(const Picture& p, const Picture& q)
  154 {
  155     Picture r;
  156     r.init(Picture::max(p.height,q.height),p.width + q.width);
  157     r.clear(p.height,0,r.height,q.width);
  158     r.clear(q.height,p.width,r.height,r.width);
  159     r.copyblock(0,0,p);
  160     r.copyblock(0,p.width,q);
  161     return r;
  162 }
  测试代码:
  1 char *init[]= {"Paris","in the","Spring"};
  2 Picture p(init,3);
  3 cout << frame(frame(p) & (p | frame(p))) << endl;
    黑客防线网安服务器维护方案本篇连接:http://www.rongsen.com.cn/show-15084-1.html
网站维护教程更新时间:2012-04-04 22:49:46  【打印此页】  【关闭
我要申请本站N点 | 黑客防线官网 |  
专业服务器维护及网站维护手工安全搭建环境,网站安全加固服务。黑客防线网安服务器维护基地招商进行中!QQ:29769479

footer  footer  footer  footer