Skip to content

Commit 06d4ab4

Browse files
committed
Memoize the properties shape, strides, and dtype
1 parent 9a9a928 commit 06d4ab4

1 file changed

Lines changed: 25 additions & 18 deletions

File tree

cuda_core/cuda/core/experimental/_memoryview.pyx

Lines changed: 25 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ cdef class StridedMemoryView:
6969
obj : Any
7070
Any objects that supports either DLPack (up to v1.0) or CUDA Array
7171
Interface (v3).
72-
stream_ptr: Optional[int]
72+
stream_ptr: int
7373
The pointer address (as Python `int`) to the **consumer** stream.
7474
Stream ordering will be properly established unless ``-1`` is passed.
7575
"""
@@ -85,6 +85,11 @@ cdef class StridedMemoryView:
8585
# A strong reference to the result of obj.__dlpack__() so we
8686
# can lazily create shape and strides from it later
8787
cdef object dlpack_capsule
88+
89+
# Memoized properties
90+
cdef tuple _shape
91+
cdef object _strides
92+
cdef object _dtype
8893

8994
def __init__(self, obj=None, stream_ptr=None):
9095
if obj is not None:
@@ -98,45 +103,47 @@ cdef class StridedMemoryView:
98103

99104
@property
100105
def shape(self) -> tuple[int]:
101-
if self.exporting_obj is not None:
106+
if self._shape is None and self.exporting_obj is not None:
102107
if self.dl_tensor != NULL:
103-
return cuda_utils.carray_int64_t_to_tuple(
108+
self._shape = cuda_utils.carray_int64_t_to_tuple(
104109
self.dl_tensor.shape,
105110
self.dl_tensor.ndim
106111
)
107112
else:
108-
return self.exporting_obj.__cuda_array_interface__["shape"]
109-
return ()
113+
self._shape = self.exporting_obj.__cuda_array_interface__["shape"]
114+
else:
115+
self._shape = ()
116+
return self._shape
110117

111118
@property
112119
def strides(self) -> Optional[tuple[int]]:
113120
cdef int itemsize
114-
if self.exporting_obj is not None:
121+
if self._strides is None and self.exporting_obj is not None:
115122
if self.dl_tensor != NULL:
116123
if self.dl_tensor.strides:
117-
return cuda_utils.carray_int64_t_to_tuple(
124+
self._strides = cuda_utils.carray_int64_t_to_tuple(
118125
self.dl_tensor.strides,
119126
self.dl_tensor.ndim
120127
)
121128
else:
122129
strides = self.exporting_obj.__cuda_array_interface__.get("strides")
123130
if strides is not None:
124131
itemsize = self.dtype.itemsize
125-
result = cpython.PyTuple_New(len(strides))
132+
self._strides = cpython.PyTuple_New(len(strides))
126133
for i in range(len(strides)):
127-
cpython.PyTuple_SET_ITEM(result, i, strides[i] // itemsize)
128-
return result
129-
return None
134+
cpython.PyTuple_SET_ITEM(self._strides, i, strides[i] // itemsize)
135+
return self._strides
130136

131137
@property
132138
def dtype(self) -> Optional[numpy.dtype]:
133-
if self.exporting_obj is not None:
134-
if self.dl_tensor != NULL:
135-
return dtype_dlpack_to_numpy(&self.dl_tensor.dtype)
136-
else:
137-
# TODO: this only works for built-in numeric types
138-
return numpy.dtype(self.exporting_obj.__cuda_array_interface__["typestr"])
139-
return None
139+
if self._dtype is None:
140+
if self.exporting_obj is not None:
141+
if self.dl_tensor != NULL:
142+
self._dtype = dtype_dlpack_to_numpy(&self.dl_tensor.dtype)
143+
else:
144+
# TODO: this only works for built-in numeric types
145+
self._dtype = numpy.dtype(self.exporting_obj.__cuda_array_interface__["typestr"])
146+
return self._dtype
140147

141148
def __repr__(self):
142149
return (f"StridedMemoryView(ptr={self.ptr},\n"

0 commit comments

Comments
 (0)