AcceleratorBuffer.hpp 7.15 KB
Newer Older
1
2
3
4
5
6
/*******************************************************************************
 * Copyright (c) 2017 UT-Battelle, LLC.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * and Eclipse Distribution License v1.0 which accompanies this
 * distribution. The Eclipse Public License is available at
7
8
 * http://www.eclipse.org/legal/epl-v10.html and the Eclipse Distribution
 *License is available at https://eclipse.org/org/documents/edl-v10.php
9
10
 *
 * Contributors:
11
12
 *   Alexander J. McCaskey - initial API and implementation
 *******************************************************************************/
13
14
15
#ifndef XACC_ACCELERATOR_ACCELERATORBUFFER_HPP_
#define XACC_ACCELERATOR_ACCELERATORBUFFER_HPP_

16
#include <boost/dynamic_bitset.hpp>
17
#include <string>
18
#include <sstream>
19
#include <iostream>
20
#include "Utils.hpp"
21

22
23
#define RAPIDJSON_HAS_STDSTRING 1
#include "rapidjson/prettywriter.h"
24
#include "rapidjson/document.h"
25
26
27
28
29

using namespace rapidjson;

#include <boost/variant.hpp>

30
31
namespace xacc {

32
33
34
35
36
class AcceleratorBuffer;

using AcceleratorBufferChildPair =
    std::pair<std::string, std::shared_ptr<AcceleratorBuffer>>;
using ExtraInfo = boost::variant<int, double, std::string, std::vector<int>,
Mccaskey, Alex's avatar
Mccaskey, Alex committed
37
38
                                 std::vector<double>, std::vector<std::string>,
                                 std::map<int, std::vector<int>>>;
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
using AddPredicate = std::function<bool(ExtraInfo &)>;

class CheckEqualVisitor : public boost::static_visitor<bool> {
private:
  ExtraInfo extraInfo;

public:
  CheckEqualVisitor(ExtraInfo &toCheck) : extraInfo(toCheck) {}
  CheckEqualVisitor(const ExtraInfo &toCheck) : extraInfo(toCheck) {}

  bool operator()(const int &i) const;
  bool operator()(const double &i) const;
  bool operator()(const std::string &i) const;
  bool operator()(const std::vector<int> &i) const;
  bool operator()(const std::vector<double> &i) const;
  bool operator()(const std::vector<std::string> &i) const;
  bool operator()(const std::map<int, std::vector<int>> &i) const;
};

class ToJsonVisitor : public boost::static_visitor<> {
private:
  PrettyWriter<StringBuffer> &writer;

public:
  ToJsonVisitor(PrettyWriter<StringBuffer> &w) : writer(w) {}

  void operator()(const int &i);
  void operator()(const double &i);
  void operator()(const std::string &i);
  void operator()(const std::vector<int> &i);
  void operator()(const std::vector<double> &i);
  void operator()(const std::vector<std::string> &i);
  void operator()(const std::map<int, std::vector<int>> &i);
};

74
/**
75
76
77
78
 * The AcceleratorBuffer models an allocated buffer of
 * bits that are operated on by a kernel. As such,
 * the AcceleratorBuffer's primary role is to store
 * Accelerator execution results.
79
80
81
82
 *
 * @author Alex McCaskey
 */
class AcceleratorBuffer {
83

84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
protected:
  /**
   * Reference to the Accelerator measurement result bit strings
   */
  std::vector<boost::dynamic_bitset<>> measurements;

  std::map<std::string, int> bitStringToCounts;

  /**
   * The name of this AcceleratorBuffer
   */
  std::string bufferId;

  /**
   * The number of bits in this buffer.
   */
  int nBits;

  std::vector<AcceleratorBufferChildPair> children;

  std::map<std::string, ExtraInfo> info;

106
public:
107
108
  AcceleratorBuffer() {}

109
110
111
  /**
   * The Constructor
   */
112
  AcceleratorBuffer(const std::string &str, const int N);
113
114

  /**
115
   * The copy constructor
116
   */
117
118
119
120
121
122
  AcceleratorBuffer(const AcceleratorBuffer &other);

  void appendChild(const std::string name,
                   std::shared_ptr<AcceleratorBuffer> buffer);
  std::vector<std::shared_ptr<AcceleratorBuffer>>
  getChildren(const std::string name);
123
  std::vector<std::shared_ptr<AcceleratorBuffer>> getChildren();
124
125
126
127
128
129
130
131
132
  std::vector<std::string> getChildrenNames();

  void addExtraInfo(const std::string infoName, ExtraInfo i);
  bool addExtraInfo(const std::string infoName, ExtraInfo i,
                    AddPredicate predicate);
  std::vector<std::string> listExtraInfoKeys();
  bool hasExtraInfoKey(const std::string infoName);
  ExtraInfo getInformation(const std::string name);
  std::map<std::string, ExtraInfo> getInformation();
133

134
135
  std::shared_ptr<AcceleratorBuffer> clone();
  
136
  const int nChildren() { return getChildren().size(); }
137
  /**
138
139
   * Return all children with ExtraInfo infoName equal
   * to the given ExtraInfo i.
140
   */
141
142
143
144
145
  std::vector<std::shared_ptr<AcceleratorBuffer>>
  getChildren(const std::string infoName, ExtraInfo i);

  // FIXME GET ALL UNIQUE ExtraInfo values at given ExtraInfo key...
  std::vector<ExtraInfo> getAllUnique(const std::string name);
146
147
148
149
150
151

  /**
   * Return the number of bits in this buffer.
   *
   * @return size The number of bits in this buffer
   */
152
  const int size() const;
153
154
155
156
157
158

  /**
   * Return this AcceleratorBuffer's name
   *
   * @return name The name of this AcceleratorBuffer
   */
159
  const std::string name() const;
160
161
162
163

  /**
   * Reset the stored measured bit strings.
   */
164
  virtual void resetBuffer();
165

166
  virtual void appendMeasurement(const std::string &measurement);
167
168
169
170
171
172

  /**
   * Add a measurement result to this Buffer
   *
   * @param measurement The measurement result
   */
173
  virtual void appendMeasurement(const boost::dynamic_bitset<> &measurement);
174
175

  virtual void appendMeasurement(const boost::dynamic_bitset<> &measurement,
176
                                 const int count);
177
178
179
  virtual void appendMeasurement(const std::string measurement,
                                 const int count);

180
  virtual double computeMeasurementProbability(const std::string &bitStr);
181
182
183
184
185
186
187
188
189
190

  /**
   * Compute and return the expectation value with respect
   * to the Pauli-Z operator. Here we provide a base implementation
   * based on an ensemble of measurement results. Subclasses
   * are free to implement this as they see fit, ie, for simulators
   * use the wavefunction.
   *
   * @return expVal The expectation value
   */
191
192
193
  virtual const double getExpectationValueZ();

  virtual void setExpectationValueZ(const double exp);
194
195
196
197
198
199

  /**
   * Return a read-only view of this Buffer's measurement results
   *
   * @return results Measurement results
   */
200
  virtual const std::vector<boost::dynamic_bitset<>> getMeasurements();
201
202
203
204
205
206

  /**
   * Return all measurements as bit strings.
   *
   * @return bitStrings List of bit strings.
   */
207
  virtual const std::vector<std::string> getMeasurementStrings();
208

209
  virtual std::map<std::string, int> getMeasurementCounts();
210
211
212
213
214
215
216
217
218
219
220
221
222
223
  virtual void clearMeasurements() {
    measurements.clear();
    bitStringToCounts.clear();
  }
  
  virtual void setMeasurements(std::map<std::string, int> counts) {
    clearMeasurements();
    bitStringToCounts = counts;
    for (auto& kv : counts) {
        for (int i = 0; i < kv.second; i++) 
           measurements.push_back(boost::dynamic_bitset<>(kv.first));
    }
  }
  
224
225
226
227
  /**
   * Print information about this AcceleratorBuffer to standard out.
   *
   */
228
  virtual void print();
229
  const std::string toString();
230
231
232
233
234
235
236

  /**
   * Print information about this AcceleratorBuffer to the
   * given output stream.
   *
   * @param stream Stream to write the buffer to.
   */
237
  virtual void print(std::ostream &stream);
238

239
240
  virtual void load(std::istream &stream);

241
242
243
244
  /**
   * The Destructor
   */
  virtual ~AcceleratorBuffer() {}
245
246
};

247
} // namespace xacc
248

249
#endif