Предупреждения и ошибки с C# Span <T>со стороны взаимодействия C ++ / CLI - PullRequest
0 голосов
/ 20 января 2020

Я пытаюсь выработать Span<T> для взаимодействия и возникают некоторые странные проблемы.

У меня есть управляемый C# проект, отвечающий за хранение числовых данных, который использует Span<T>. Чтобы сослаться на несколько Span<T> одновременно, они инкапсулированы в другую структуру ref, которая в упрощенном коде выглядит следующим образом:

    public readonly ref struct DataSelection
    {
        private readonly Span<Position3d> _PointsSpan;
        private readonly Span<UnitVector3d> _NormalsSpan;

        internal DataSelection(Span<Position3d> points, Span<UnitVector3d> normals)
        {
            _PointsSpan = points;
            _NormalsSpan = normals;
        }

        public DataSelection(Position3d[] points, UnitVector3d[] normals) : this(points, normals)
        {
        }

        public unsafe DataSelection(Position3d* points, UnitVector3d* normals, int count) : this(new Span<Position3d>(points, count), new Span<Position3d>(normals, count))
        {
        }

        public int Count => _PointsSpan.Length;

        public Span<Position3d> Points => _PointsSpan;

        public Span<UnitVector3d> Normals => _NormalsSpan;
    }

EDIT : Для справки Position3d и UnitVector3d - это простые структуры значений, которые в основном сводятся к трем двойным значениям:

[StructLayout(LayoutKind.Sequential)]
public readonly struct Position3d
{
    private readonly double _X;
    private readonly double _Y;
    private readonly double _Z;

    public Position3d(double x, double y, double z)
    {
        _X = x;
        _Y = y;
        _Z = z;
    }

    public double X => _X;

    public double Y => _Y;

    public double Z => _Z;
}

Предполагается, что DataSelection можно использовать для определения операций над положением и нормальным массивы, без ограничения того, находятся ли данные в управляемой или собственной памяти. Таким образом, фактическая работа выполняется другими классами, которые я сейчас опускаю.

Однако взаимодействие с native осуществляется в проекте C ++ / CLI (не мой выбор). Там я могу сделать либо

array<Position3d>^ posDataArr = gcnew array<Position3d> { Position3d(1, 2, 3), Position3d(4, 5, 6), Position3d(7, 8, 9) };
auto selection = DataSelection(posDataArr); // Note: there is a constructor with only position that I have omitted above.

, либо

double *posData = new double[9]{ 1, 2, 3, 4, 5, 6, 7, 8, 9 };
auto selection = DataSelection(reinterpret_cast<Position3d*>(posData), 3);

в качестве контрольного примера для работы с управляемыми или собственными данными. Все работает нормально с тем же функциональным конечным результатом.

Однако любой вызов любого метода в DataSelection приводит к Warning C4996 'XY': was declared deprecated. Предупреждение не появляется для свойств.

Если я заменю auto selection на явное объявление DataSelection selection, я получу Error C4950 '[...]::DataSelection': marked as obsolete.

Что здесь происходит, почему компилятор жалуется , но он все еще работает, как ожидалось?

...