提交 73b95fa0 authored 作者: Ian Goodfellow's avatar Ian Goodfellow

removed Value class

上级 9a539c65
...@@ -448,8 +448,8 @@ class Method(Component): ...@@ -448,8 +448,8 @@ class Method(Component):
if input not in _inputs: if input not in _inputs:
# Add this input to the inputs; we require that storage already exists for them, # Add this input to the inputs; we require that storage already exists for them,
# but otherwise they are immutable. # but otherwise they are immutable.
if isinstance(input, gof.Value): # and not isinstance(input, gof.Constant): if isinstance(input, gof.Constant):
#input might be Value or Constant #input might be Constant
storage = get_storage(input) storage = get_storage(input)
assert type(storage) is io.In assert type(storage) is io.In
......
...@@ -431,7 +431,7 @@ class CLinker(link.Linker): ...@@ -431,7 +431,7 @@ class CLinker(link.Linker):
# The orphans field is listified to ensure a consistent order. # The orphans field is listified to ensure a consistent order.
#list(env.orphans.difference(self.outputs)) #list(env.orphans.difference(self.outputs))
self.orphans = list(r for r in self.variables self.orphans = list(r for r in self.variables
if isinstance(r, graph.Value) and if isinstance(r, graph.Constant) and
r not in self.inputs) r not in self.inputs)
self.temps = list(set(self.variables).difference( self.temps = list(set(self.variables).difference(
self.inputs).difference(self.outputs).difference(self.orphans)) self.inputs).difference(self.outputs).difference(self.orphans))
...@@ -497,8 +497,8 @@ class CLinker(link.Linker): ...@@ -497,8 +497,8 @@ class CLinker(link.Linker):
policy = [[get_nothing, get_nothing, get_nothing], policy = [[get_nothing, get_nothing, get_nothing],
[get_c_declare, get_c_extract, get_c_cleanup]] [get_c_declare, get_c_extract, get_c_cleanup]]
elif variable in self.orphans: elif variable in self.orphans:
if not isinstance(variable, graph.Value): if not isinstance(variable, graph.Constant):
raise TypeError("All orphans to CLinker must be Value" raise TypeError("All orphans to CLinker must be Constant"
" instances.", variable) " instances.", variable)
if isinstance(variable, graph.Constant): if isinstance(variable, graph.Constant):
try: try:
......
...@@ -240,7 +240,7 @@ class Env(utils.object2): ...@@ -240,7 +240,7 @@ class Env(utils.object2):
r_owner_done.add(node) r_owner_done.add(node)
self.__import__(node) self.__import__(node)
for r in variables: for r in variables:
if r.owner is None and not isinstance(r, graph.Value) and r not in self.inputs: if r.owner is None and not isinstance(r, graph.Constant) and r not in self.inputs:
raise MissingInputError("Undeclared input", r) raise MissingInputError("Undeclared input", r)
if not getattr(r, 'env', None) is self: if not getattr(r, 'env', None) is self:
self.__setup_r__(r) self.__setup_r__(r)
...@@ -260,7 +260,7 @@ class Env(utils.object2): ...@@ -260,7 +260,7 @@ class Env(utils.object2):
for r in node.inputs: for r in node.inputs:
if hasattr(r, 'env') and r.env is not self: if hasattr(r, 'env') and r.env is not self:
raise Exception("%s is already owned by another env" % r) raise Exception("%s is already owned by another env" % r)
if r.owner is None and not isinstance(r, graph.Value) and r not in self.inputs: if r.owner is None and not isinstance(r, graph.Constant) and r not in self.inputs:
#Verbose error message #Verbose error message
#Show a complete chain of variables from the missing input to an output #Show a complete chain of variables from the missing input to an output
...@@ -610,7 +610,7 @@ class Env(utils.object2): ...@@ -610,7 +610,7 @@ class Env(utils.object2):
excess = self.variables.difference(variables) excess = self.variables.difference(variables)
raise Exception("The variables are inappropriately cached. missing, in excess: ", missing, excess) raise Exception("The variables are inappropriately cached. missing, in excess: ", missing, excess)
for variable in variables: for variable in variables:
if variable.owner is None and variable not in self.inputs and not isinstance(variable, graph.Value): if variable.owner is None and variable not in self.inputs and not isinstance(variable, graph.Constant):
raise Exception("Undeclared input.", variable) raise Exception("Undeclared input.", variable)
if variable.env is not self: if variable.env is not self:
raise Exception("Variable should belong to the env.", variable) raise Exception("Variable should belong to the env.", variable)
......
...@@ -323,23 +323,18 @@ class Variable(utils.object2): ...@@ -323,23 +323,18 @@ class Variable(utils.object2):
raise NotImplementedError('Subclasses of Variable must provide __ge__', raise NotImplementedError('Subclasses of Variable must provide __ge__',
self.__class__.__name__) self.__class__.__name__)
class Value(Variable): class Constant(Variable):
""" """
A :term:`Value` is a `Variable` with a default value. A :term:`Constant` is a `Variable` with a `value` field that cannot be changed at runtime.
Its owner field is always None. And since it has a default value, a `Value` instance need
not be named as an input to `compile.function`.
This kind of node is useful because when a value is known at compile time, more
optimizations are possible.
Constant nodes make eligible numerous optimizations: constant inlining in C code, constant folding, etc.
""" """
#__slots__ = ['data'] #__slots__ = ['data']
def __init__(self, type, data, name = None): def __init__(self, type, data, name = None):
"""Initialize self. """Initialize self.
:note: :note:
The data field is filtered by what is provided in the constructor for the Value's The data field is filtered by what is provided in the constructor for the Constant's
type field. type field.
WRITEME WRITEME
...@@ -347,45 +342,14 @@ class Value(Variable): ...@@ -347,45 +342,14 @@ class Value(Variable):
""" """
Variable.__init__(self, type, None, None, name) Variable.__init__(self, type, None, None, name)
self.data = type.filter(data) self.data = type.filter(data)
def __str__(self):
"""WRITEME"""
if self.name is not None:
return self.name
return "<" + str(self.data) + ">" #+ "::" + str(self.type)
def clone(self):
"""WRITEME"""
#return copy(self)
cp = self.__class__(self.type, copy(self.data), self.name)
cp.tag = copy(self.tag)
return cp
def __set_owner(self, value):
"""WRITEME
:Exceptions:
- `ValueError`: if `value` is not `None`
"""
if value is not None:
raise ValueError("Value instances cannot have an owner.")
owner = property(lambda self: None, __set_owner)
value = property(lambda self: self.data,
doc='read-only data access method')
# index is not defined, because the `owner` attribute must necessarily be None
class Constant(Value):
"""
A :term:`Constant` is a `Value` that cannot be changed at runtime.
Constant nodes make eligible numerous optimizations: constant inlining in C code, constant folding, etc.
"""
#__slots__ = ['data']
def __init__(self, type, data, name = None):
Value.__init__(self, type, data, name)
def equals(self, other): def equals(self, other):
# this does what __eq__ should do, but Variable and Apply should always be hashable by id # this does what __eq__ should do, but Variable and Apply should always be hashable by id
return isinstance(other, Constant) and self.signature() == other.signature() return isinstance(other, Constant) and self.signature() == other.signature()
def signature(self): def signature(self):
return (self.type, self.data) return (self.type, self.data)
def __str__(self): def __str__(self):
if self.name is not None: if self.name is not None:
return self.name return self.name
...@@ -404,6 +368,21 @@ class Constant(Value): ...@@ -404,6 +368,21 @@ class Constant(Value):
cp.tag = copy(self.tag) cp.tag = copy(self.tag)
return cp return cp
def __set_owner(self, value):
"""WRITEME
:Exceptions:
- `ValueError`: if `value` is not `None`
"""
if value is not None:
raise ValueError("Constant instances cannot have an owner.")
owner = property(lambda self: None, __set_owner)
value = property(lambda self: self.data,
doc='read-only data access method')
# index is not defined, because the `owner` attribute must necessarily be None
def stack_search(start, expand, mode='bfs', build_inv = False): def stack_search(start, expand, mode='bfs', build_inv = False):
"""Search through a graph, either breadth- or depth-first """Search through a graph, either breadth- or depth-first
......
...@@ -286,7 +286,7 @@ def map_storage(env, order, input_storage, output_storage): ...@@ -286,7 +286,7 @@ def map_storage(env, order, input_storage, output_storage):
for node in order: for node in order:
for r in node.inputs: for r in node.inputs:
if r not in storage_map: if r not in storage_map:
assert isinstance(r, graph.Value) assert isinstance(r, graph.Constant)
storage_map[r] = [r.data] storage_map[r] = [r.data]
for r in node.outputs: for r in node.outputs:
storage_map.setdefault(r, [None]) storage_map.setdefault(r, [None])
......
...@@ -354,12 +354,6 @@ class SparseConstant(gof.Constant, _sparse_py_operators): ...@@ -354,12 +354,6 @@ class SparseConstant(gof.Constant, _sparse_py_operators):
def __repr__(self): def __repr__(self):
return str(self) return str(self)
class SparseValue(gof.Value, _sparse_py_operators):
dtype = property(lambda self: self.type.dtype)
format = property(lambda self: self.type.format)
class SparseType(gof.Type): class SparseType(gof.Type):
""" """
@type dtype: numpy dtype string such as 'int64' or 'float64' (among others) @type dtype: numpy dtype string such as 'int64' or 'float64' (among others)
......
...@@ -12,7 +12,7 @@ import numpy ...@@ -12,7 +12,7 @@ import numpy
import theano import theano
from theano.configparser import config from theano.configparser import config
from theano import gof from theano import gof
from theano.gof import Apply, Constant, Op, Type, Value, Variable from theano.gof import Apply, Constant, Op, Type, Variable
import elemwise import elemwise
from theano import scalar as scal from theano import scalar as scal
...@@ -390,12 +390,6 @@ def constant(x, name=None, ndim=None, dtype=None): ...@@ -390,12 +390,6 @@ def constant(x, name=None, ndim=None, dtype=None):
return constant_or_value(x, rtype=TensorConstant, name=name, ndim=ndim, return constant_or_value(x, rtype=TensorConstant, name=name, ndim=ndim,
dtype=dtype) dtype=dtype)
def value(x, name=None, ndim=None, dtype=None):
return constant_or_value(x, rtype=TensorValue, name=name,
ndim=ndim, dtype=dtype)
def _obj_is_wrappable_as_tensor(x): def _obj_is_wrappable_as_tensor(x):
try: try:
constant(x) constant(x)
...@@ -1784,14 +1778,6 @@ class TensorConstant(_tensor_py_operators, Constant): ...@@ -1784,14 +1778,6 @@ class TensorConstant(_tensor_py_operators, Constant):
TensorType.Constant = TensorConstant TensorType.Constant = TensorConstant
class TensorValue(_tensor_py_operators, Value):
"""Subclass to add the tensor operators to the basic `Value` class.
To create a TensorValue, use the `value` function in this module.
:note: Value is deprecated by SharedVariable
"""
Tensor = TensorType Tensor = TensorType
...@@ -1801,7 +1787,7 @@ elemwise.as_tensor_variable = as_tensor_variable ...@@ -1801,7 +1787,7 @@ elemwise.as_tensor_variable = as_tensor_variable
elemwise.TensorType = TensorType elemwise.TensorType = TensorType
elemwise.TensorVariable = TensorVariable elemwise.TensorVariable = TensorVariable
elemwise.TensorConstant = TensorConstant elemwise.TensorConstant = TensorConstant
elemwise.TensorValue = TensorValue #elemwise.TensorValue = TensorValue
######################### #########################
......
import numpy import numpy
import theano import theano
from theano import gof from theano import gof
from theano.gof import Apply, Constant, Generic, Op, Type, Value, Variable from theano.gof import Apply, Constant, Generic, Op, Type, Variable
from basic import tensor from basic import tensor
########################## ##########################
# Disk Access # Disk Access
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论