-
Notifications
You must be signed in to change notification settings - Fork 5.3k
Closed
Labels
api-approvedAPI was approved in API review, it can be implementedAPI was approved in API review, it can be implementedarea-System.Numerics.Tensorsin-prThere is an active PR which will close this issue when it is mergedThere is an active PR which will close this issue when it is merged
Milestone
Description
Background and motivation
We currently do not have a non-generic base type for Tensor. This is fine, but there are many times you need info about the Tensor (its rank, lengths of dimenions, etc) and you can get this info without needing to know or care about the generic type itself. We need to add a base type that will better facilitate this.
I've added some basic access via boxing for the most general applications.
API Proposal
namespace System.Numerics.Tensors;
// All of these existed in higher types. Just creating a new base type and moving these down.
+ public interface IReadOnlyTensor
+ {
+ /// <summary>
+ /// Gets a value that indicates whether the collection is currently empty.
+ /// </summary>
+ bool IsEmpty { get; }
+ /// <summary>
+ /// Gets a value that indicates whether the underlying buffer is pinned.
+ /// </summary>
+ bool IsPinned { get; }
+ /// <summary>
+ /// Gets the number of elements in the tensor.
+ /// </summary>
+ nint FlattenedLength { get; }
+ /// <summary>
+ /// Gets the number of dimensions in the tensor.
+ /// </summary>
+ int Rank { get; }
+ /// <summary>
+ /// Gets the length of each dimension in the tensor.
+ /// </summary>
+ [UnscopedRef]
+ ReadOnlySpan<nint> Lengths { get; }
+ /// <summary>
+ /// Gets the stride of each dimension in the tensor.
+ /// </summary>
+ [UnscopedRef]
+ ReadOnlySpan<nint> Strides { get; }
+ /// <summary>
+ /// Gets the value at the specified indexes.
+ /// </summary>
+ /// <param name="indexes">The indexes to be used.</param>
+ object this[params scoped ReadOnlySpan<nint> indexes] { get; }
+ /// <summary>
+ /// Gets the value at the specified indexes.
+ /// </summary>
+ /// <param name="indexes">The indexes to be used.</param>
+ object this[params scoped ReadOnlySpan<NIndex> indexes] { get; }
+ }
+ public interface ITensor : IReadOnlyTensor
+ {
+ /// <summary>
+ /// Gets the value at the specified indexes.
+ /// </summary>
+ /// <param name="indexes">The indexes to be used.</param>
+ object this[params scoped ReadOnlySpan<nint> indexes] { get; set; }
+ /// <summary>
+ /// Gets the value at the specified indexes.
+ /// </summary>
+ /// <param name="indexes">The indexes to be used.</param>
+ object this[params scoped ReadOnlySpan<NIndex> indexes] { get; set; }
+ /// <summary>
+ /// Gets a value that indicates whether the collection is read-only.
+ /// </summary>
+ bool IsReadOnly { get; }
+ /// <summary>
+ /// Clears the tensor.
+ /// </summary>
+ void Clear();
+ /// <summary>
+ /// Fills the contents of this tensor with the given value.
+ /// </summary>
+ void Fill(object value);
+ }
// And we are removing these methods from the typed base interfaces
public interface IReadOnlyTensor<TSelf, T> : IReadOnlyTensor, IEnumerable<T>
where TSelf : IReadOnlyTensor<TSelf, T>
{
- /// <summary>
- /// Gets a value that indicates whether the collection is currently empty.
- /// </summary>
- bool IsEmpty { get; }
- /// <summary>
- /// Gets a value that indicates whether the underlying buffer is pinned.
- /// </summary>
- bool IsPinned { get; }
- /// <summary>
- /// Gets the number of elements in the tensor.
- /// </summary>
- nint FlattenedLength { get; }
- /// <summary>
- /// Gets the number of dimensions in the tensor.
- /// </summary>
- int Rank { get; }
- /// <summary>
- /// Gets the length of each dimension in the tensor.
- /// </summary>
- [UnscopedRef]
- ReadOnlySpan<nint> Lengths { get; }
- /// <summary>
- /// Gets the stride of each dimension in the tensor.
- /// </summary>
- [UnscopedRef]
- ReadOnlySpan<nint> Strides { get; }
}
public interface ITensor<TSelf, T> : ITensor, IReadOnlyTensor<TSelf, T>
where TSelf : ITensor<TSelf, T>
{
- /// <summary>
- /// Gets a value that indicates whether the collection is read-only.
- /// </summary>
- bool IsReadOnly { get; }
- /// <summary>
- /// Clears the tensor.
- /// </summary>
- void Clear();
}API Usage
public void DoStuffWithNonGenericTensor(ITensor tensor);
Tensor<int> tensor = Tensor.Create<int>([1, 2, 3, 4], [2, 2]);
DoStuffWithNonGenericTensor(tensor);Alternative Designs
We may decide we don't want access to the data via boxing, in which case we can remove those methods.
Risks
Low risk because it's a preview type, but because we are changing the class hierarchy there is more than none.
Metadata
Metadata
Assignees
Labels
api-approvedAPI was approved in API review, it can be implementedAPI was approved in API review, it can be implementedarea-System.Numerics.Tensorsin-prThere is an active PR which will close this issue when it is mergedThere is an active PR which will close this issue when it is merged