Un/pack (arrays of) complex floats
It would be very convenient to be able to send (arrays of) complex floats over the wire. Msgpack has support for (arrays of) floats (as does JSON, sorta), but it restricts itself to the real case. We should expose an appropriate RPCQ type and to piggyback complex float packing on top of the existing float packing.
Easy enough to define a new :complex type and have it serialize. How to deserialize is unclear to me though, since at that point it looks equivalent to a list of floats (and deserializes as such).
diff --git a/src/rpcq.lisp b/src/rpcq.lisp
index 9751c16..b82ae50 100644
--- a/src/rpcq.lisp
+++ b/src/rpcq.lisp
@@ -32,7 +32,7 @@
(deftype atom-type ()
- '(member :string :bytes :bool :float :integer :any))
+ '(member :string :bytes :bool :float :complex :integer :any))
(defun format-documentation-string (string)
@@ -69,10 +69,14 @@ The input strings are assumed to be FORMAT-compatible, so sequences like ~<newli
(defmethod %serialize ((payload cons))
(loop :for elt :in payload :collect (%serialize elt)))
+(defmethod %serialize ((payload complex))
+ (%serialize (list (realpart payload)
+ (imagpart payload))))
+
(defmethod %serialize ((payload hash-table))
(let ((hash (make-hash-table :test #'equal)))
(loop :for k :being :the :hash-keys :of payload
- :using (hash-value v)
+ :using (hash-value v)
:do (setf (gethash (%serialize k) hash) (%serialize v)))
hash))
@@ -117,7 +121,7 @@ whether the field is REQUIRED and a specified DEFAULT value.
The primitive field types must be specified as one of
- :string :bytes :integer :float :bool
+ :string :bytes :integer :complex :float :bool
Message field types are specified by their class name, e.g. for
a Calibration message the field type is
@@ -129,7 +133,7 @@ List and mapping field types are specified as
(:list x) (:map :string -> x)
where x is one of
-{:string, :bytes, :any, :integer, :float, :bool, :list, :mapping} or a
+{:string, :bytes, :any, :integer, :complex, :float, :bool, :list, :mapping} or a
message field type. We currently only support :string keys for
mappings as JSON does not support other kinds of keys but we
nonetheless explicitly include the key type for better readability
@@ -153,7 +157,7 @@ We distinguish between the following options for any field type:
"
(cond
- ;; handle :string :integer :float :bool :bytes
+ ;; handle :string :integer :float :complex :bool :bytes
((keywordp field-type)
(check-type field-type atom-type)
(let*
@@ -161,6 +165,7 @@ We distinguish between the following options for any field type:
:bytes (simple-array (unsigned-byte 8))
:integer fixnum
:float double-float
+ :complex complex
:bool boolean
:any t)
field-type))
(rpcq:deserialize (rpcq::serialize (list #C(1.234 0.045) #C(1.234 0.045) #C(1.234 0.045))))
((1.234 0.045) (1.234 0.045) (1.234 0.045))
An update: I have modified cl-messagepack to (IMO) better support messagepack's extension format. Something @stylewarning said distracted me from the problem though: a neat feature of the HTTP interface is that, for the wavefunction request, it doesn't need to load the entire wavefunction into memory, but can stream the wavefunction amplitude-by-amplitude. (Becomes important when the wavefunction is mucho grande.) I don't think RPCQ currently allows for this mode of operation, and I don't know if it should. Something to consider though.
Sounds quite tricky to arrange in RPCQ.
Streaming in RPCQ would also be nice for QPU results.