Skip to content

Commit

Permalink
Showing 4 changed files with 70 additions and 7 deletions.
6 changes: 5 additions & 1 deletion dimod/binary/binary_quadratic_model.py
Original file line number Diff line number Diff line change
@@ -37,7 +37,7 @@
from dimod.binary.pybqm import pyBQM
from dimod.binary.vartypeview import VartypeView
from dimod.decorators import forwarding_method
from dimod.serialization.fileview import SpooledTemporaryFile, _BytesIO, VariablesSection
from dimod.serialization.fileview import SpooledTemporaryFile, _BytesIO, VariablesSection, load
from dimod.sym import Eq, Ge, Le
from dimod.typing import Bias, Variable
from dimod.variables import Variables, iter_deserialize_variables
@@ -1909,3 +1909,7 @@ def as_bqm(*args, cls: None = None, copy: bool = False,
return bqm

return BinaryQuadraticModel(*args, dtype=dtype)


# register fileview loader
load.register(BQM_MAGIC_PREFIX, BinaryQuadraticModel.from_file)
6 changes: 5 additions & 1 deletion dimod/discrete/discrete_quadratic_model.py
Original file line number Diff line number Diff line change
@@ -25,7 +25,7 @@

from dimod.discrete.cydiscrete_quadratic_model import cyDiscreteQuadraticModel
from dimod.sampleset import as_samples
from dimod.serialization.fileview import VariablesSection, _BytesIO, SpooledTemporaryFile
from dimod.serialization.fileview import VariablesSection, _BytesIO, SpooledTemporaryFile, load
from dimod.variables import Variables
from typing import List, Tuple, Union, Generator

@@ -803,3 +803,7 @@ def to_numpy_vectors(self):


DQM = DiscreteQuadraticModel # alias


# register fileview loader
load.register(DQM_MAGIC_PREFIX, DiscreteQuadraticModel.from_file)
46 changes: 41 additions & 5 deletions dimod/serialization/fileview.py
Original file line number Diff line number Diff line change
@@ -19,6 +19,8 @@
import tempfile
import warnings

from typing import ByteString, Callable, Mapping

import numpy as np

from dimod.variables import iter_deserialize_variables, iter_serialize_variables
@@ -221,8 +223,16 @@ def seekable(self):
return True


_loaders: Mapping[bytes, Callable] = dict()


def register(prefix: bytes, loader: Callable):
"""Register a new loader."""
_loaders[prefix] = loader


def load(fp, cls=None):
"""Load a binary quadratic model from a file.
"""Load a model from a file.
Args:
fp (bytes-like/file-like):
@@ -233,9 +243,35 @@ def load(fp, cls=None):
Deprecated keyword argument. Is ignored.
Returns:
The loaded bqm.
The loaded model.
"""
# todo: handle DQM
from dimod.binary.binary_quadratic_model import BinaryQuadraticModel
return BinaryQuadraticModel.from_file(fp)
if cls is not None:
warnings.warn("'cls' keyword argument is deprecated and ignored",
DeprecationWarning, stacklevel=2)

if isinstance(fp, ByteString):
file_like: BinaryIO = _BytesIO(fp) # type: ignore[assignment]
else:
file_like = fp

if not file_like.seekable:
raise ValueError("expected file-like to be seekable")

pos = file_like.tell()

lengths = sorted(set(map(len, _loaders)))
for num_bytes in lengths:
prefix = file_like.read(num_bytes)
file_like.seek(pos)

try:
return _loaders[prefix](file_like)
except KeyError:
pass

raise ValueError("cannot load the given file-like")


# for slightly more explicit naming
load.register = register
19 changes: 19 additions & 0 deletions tests/test_serialization_fileview.py
Original file line number Diff line number Diff line change
@@ -173,3 +173,22 @@ def test_unhashable_variables(self, name, BQM, version):
new = load(fv)

self.assertEqual(new, bqm)


class TestLoad(unittest.TestCase):
def test_bqm(self):
bqm = BinaryQuadraticModel({'a': -1}, {'ab': 1}, 7, 'SPIN')
self.assertEqual(bqm, load(bqm.to_file()))

def test_dqm(self):
dqm = dimod.DiscreteQuadraticModel()
dqm.add_variable(5, 'a')
dqm.add_variable(6, 'b')
dqm.set_quadratic_case('a', 0, 'b', 5, 1.5)

new = load(dqm.to_file())

self.assertEqual(dqm.num_variables(), new.num_variables())
self.assertEqual(dqm.num_cases(), new.num_cases())
self.assertEqual(dqm.get_quadratic_case('a', 0, 'b', 5),
new.get_quadratic_case('a', 0, 'b', 5))

0 comments on commit 1c2291c

Please sign in to comment.