2013-03-28 3 views
2

У меня есть одна функция Foo, которая принимает неуправляемый тип, то я создать общую-структуру, которые требуют параметра типа для неуправляемых:Почему общая структура, параметризованная типом blittable, не является неуправляемым типом?

[<Struct>] 
type Vector4<'T when 'T:unmanaged> = 
    val x : 'T 
    val y : 'T 
    val z : 'T 
    val w : 'T 
    new (x, y, z, w) = { x = x; y = y; z = z; w = w } 

let foo<'T when 'T:unmanaged> (o:'T) = 
    printfn "%A" o 
    printfn "%d" sizeof<'T> 

let bar() = 
    let o = Vector4<float32>(1.0f, 2.0f, 3.0f, 4.0f) 
    foo o // here has error 

но я получил компиляцию ошибки:

Error 4 A generic construct requires that the type 'Vector4<float32>' is an unmanaged type 

Я проверил MSDN это СЯС:

The provided type must be an unmanaged type. Unmanaged types are either certain primitive types (sbyte, byte, char, nativeint, unativeint, float32, float, int16, uint16, int32, uint32, int64, uint64, or decimal), enumeration types, nativeptr<_>, or a non-generic structure whose fields are all unmanaged types.

Почему общая структура, которая требует параметр blittable типа не неуправляемый тип?

ответ

1

Универсальные типы не поддерживаются Interop: [1], [2]

The COM model does not support the concept of generic types. Consequently, generic types cannot be used directly for COM interop.

Тип псевдоним не поможет в данном случае, к сожалению:

[<Struct>] 
[<StructLayout(LayoutKind.Sequential)>] 
type Vector4<'T when 'T:unmanaged> = 
    val x : 'T 
    val y : 'T 
    val z : 'T 
    val w : 'T 
    new (x, y, z, w) = { x = x; y = y; z = z; w = w } 

type Vector4float = Vector4<float32> 

let inline foo<'T when 'T:unmanaged> (o:'T) = 
    printfn "%A" o 
    printfn "%d" sizeof<'T> 

let bar() = 
    let o = new Vector4float(1.0f, 2.0f, 3.0f, 4.0f) 
    foo o // A generic construct requires that the type 'Vector4float' is an unmanaged type 
+0

Спасибо, на самом деле, я не делаю COM Interop, но с функцией C PInvoke. Мне нужен тип blittable, который имеет тот же макет в памяти. Это тоже невозможно? –

+0

", который имеет тот же макет в памяти" - как вы могли бы гарантировать его с помощью типового типа? 'Vector4 ' и 'Vector4 ' будет иметь разный макет, вот в чем смысл. –

+0

Я имею в виду, имеет тот же макет в .NET и на C, потому что код C обработает его. Итак, мой вопрос: если я удалю ограничение неуправляемого, тогда я могу привязать этот объект, а затем получить закрепленный указатель, и могу ли я отправить этот указатель на C? –

Смежные вопросы