zoukankan      html  css  js  c++  java
  • C++进阶--Named Parameter Idiom

    //############################################################################
    /* Named Parameter Idiom */
    
    /* 主要解决的问题
    C++函数只支持位置参数,不支持像Python那样的命名参数
    */
    
    
    class OpenFile {
    public:
       OpenFile(string filename, bool readonly=true, bool appendWhenWriting=false, 
                int blockSize=256, bool unbuffered=true, bool exclusiveAccess=false);
    }
    
    //像下面的函数调用,我得记得每个参数的意思和位置,非常不方便,可读性差,而且不灵活
    OpenFile pf = OpenFile("foo.txt", true, false, 1024, true, true);
    
    
    // 理想的情况是像下面这样的:
    OpenFile pf = OpenFile(.filename("foo.txt"), .blockSize(1024) );
    
    
    /* 解决方法 1 */
    class OpenFile {
    public:
      OpenFile(std::string const& filename);
      OpenFile& readonly(bool ro)  { readonly_ = ro; return *this; }
      OpenFile& createIfNotExist(bool c) { createIfNotExist_ = c; return *this; }
      OpenFile& blockSize(unsigned nbytes) { blockSize_ = nbytes; return *this; }
      ...
    };
    
    OpenFile f = OpenFile("foo.txt")
               .blockSize(1024)
               .createIfNotExist(true)
               .appendWhenWriting(true)
               .unbuffered(false)
               .readonly(true)
               .exclusiveAccess(false);
    
    OpenFile f = OpenFile("foo.txt").blockSize(1024);
    
    
    /* 问题: 
     * 如果是非成员函数呢? 
     */
    
    /* 方法 2: 使用类型*/
    
    void setBirthDate(int month, int day, int year);
    
    setBirthDate(3, 1, 2012);  // 1月3日还是3月1日?
    
    
    
    //定义结构体类型
    struct Day {
       explicit Day(int d):val(d){}  //设置为explicit,不能隐式转换
       int val;
    }
    struct Month {
       explicit Month(int d):val(d){}  //设置为explicit,不能隐式转换
       int val;
    }
    struct Year {
       explicit Year(int d):val(d){}  //设置为explicit,不能隐式转换
       int val;
    }
    void setBirthDate(Month m, Day d, Year y);
    
    
    
    setBirthDate(Month(3), Day(1), Year(2010)); //正确
    setBirthDate(3, 1, 2010);  // 编译不过,很难使用出错
    
    //############################################################################
    /* Template Specialization for STL 
     * 
     * Specialize the standard library templates' behavior for our class
     *
     * std:: is a special namespace where we are not allowed to alter its contents
     * But we can specialize them for our types
     */
    
    class collar;
    
    class dog {
       collar* pCollar;
    	dog(string name = "Bob") {pCollar = new collar(); cout << name << " is born." << endl; }
    }
    
    int main() {
       dog dog1("Henry");
       dog dog2("Boq");
       std::swap(dog1, dog2); 
    }
    
  • 相关阅读:
    docker基本命令
    服务器端使用DeferredResult异步推送技术
    单链表输出倒数第k个结点值(栈实现)
    fork炸弹
    BlockingQueue实现阻塞队列
    C#工作笔记
    实现一个简单的Log框架
    (转载)在spring的bean中注入内部类
    Spring整合Hessian
    spring整合axis2(最小配置化)的示例
  • 原文地址:https://www.cnblogs.com/logchen/p/10182733.html
Copyright © 2011-2022 走看看