text: #include <vector>
  
  #include "caffe/filler.hpp"
  #include "caffe/layer.hpp"
  #include "caffe/vision_layers.hpp"
  
  namespace caffe {
  
  template <typename Dtype>
  void DummyDataLayer<Dtype>::LayerSetUp(const vector<Blob<Dtype>*>& bottom,
        const vector<Blob<Dtype>*>& top) {
    const int num_top = top.size();
    const DummyDataParameter& param = this->layer_param_.dummy_data_param();
    const int num_data_filler = param.data_filler_size();
    CHECK(num_data_filler == 0 || num_data_filler == 1 ||
          num_data_filler == num_top)
        << "Number of data fillers must be 0, 1 or equal to the number of tops: "
        << num_top << "; you specified " << num_data_filler << " data fillers.";
    CHECK(param.num_size() == 1 || param.num_size() == num_top)
        << "Must specify either a single (1) 'num' or one for each top blob "
        << "(" << num_top << "); you specified " << param.num_size() << ".";
    CHECK(param.channels_size() == 1 || param.channels_size() == num_top)
        << "Must specify either a single (1) 'channels' or one for each top blob "
        << "(" << num_top << "); you specified " << param.channels_size() << ".";
    CHECK(param.height_size() == 1 || param.height_size() == num_top)
        << "Must specify either a single (1) 'height' or one for each top blob "
        << "(" << num_top << "); you specified " << param.height_size() << ".";
    CHECK(param.width_size() == 1 || param.width_size() == num_top)
        << "Must specify either a single (1) 'width' or one for each top blob "
        << "(" << num_top << "); you specified " << param.width_size() << ".";
    // refill_[i] tells Forward i whether or not to actually refill top Blob i.
    // If refill_[i] is false, Forward does nothing for Blob i. We use this to
    // avoid wastefully refilling "constant" Blobs in every forward pass.
    // We first fill refill_ in with the INVERSE of its final values.
    // The first time we run Forward from the LayerSetUp method, we'll fill only
    // Blobs for which refill_ is normally false.  These Blobs will never be
    // filled again.
    refill_.clear();
    fillers_.clear();
    if (num_data_filler <= 1) {
      FillerParameter filler_param;
      if (num_data_filler == 0) {
        filler_param.set_type("constant");
        filler_param.set_value(0);
      } else {
        filler_param.CopyFrom(param.data_filler(0));
      }
      // Refill on each iteration iff not using a constant filler,
      // but use the inverse of this rule for the first run.
      refill_.resize(1);
      refill_[0] = (strcmp(filler_param.type().c_str(), "constant") == 0);
      fillers_.resize(1);
      fillers_[0].reset(GetFiller<Dtype>(filler_param));
    } else {
      refill_.resize(num_top);
      fillers_.resize(num_top);
      for (int i = 0; i < num_top; ++i) {
        fillers_[i].reset(GetFiller<Dtype>(param.data_filler(i)));
        // Refill on each iteration iff not using a constant filler,
        // but use the inverse of this rule for the first run.
        refill_[i] =
            (strcmp(param.data_filler(i).type().c_str(), "constant") == 0);
      }
    }
    for (int i = 0; i < num_top; ++i) {
      const int num = (param.num_size() == 1) ? param.num(0) : param.num(i);
      const int channels =
          (param.channels_size() == 1) ? param.channels(0) : param.channels(i);
      const int height =
          (param.height_size() == 1) ? param.height(0) : param.height(i);
      const int width =
          (param.width_size() == 1) ? param.width(0) : param.width(i);
      top[i]->Reshape(num, channels, height, width);
    }
    // Run Forward once, with refill_ inverted, to fill the constant Blobs.
    this->Forward(bottom, top);
    // Invert the inverted refill_ values to refill the desired (non-constant)
    // Blobs in every usual forward pass.
    for (int i = 0; i < refill_.size(); ++i) {
      refill_[i] = !refill_[i];
    }
  }
  
  template <typename Dtype>
  void DummyDataLayer<Dtype>::Forward_cpu(const vector<Blob<Dtype>*>& bottom,
        const vector<Blob<Dtype>*>& top) {
    for (int i = 0; i < top.size(); ++i) {
      const int filler_id = (fillers_.size() > 1) ? i : 0;
      if (refill_[filler_id]) {
        fillers_[filler_id]->Fill(top[i]);
      }
    }
  }
  
  INSTANTIATE_CLASS(DummyDataLayer);
  REGISTER_LAYER_CLASS(DummyData);
  
  }  // namespace caffe
  