6

OpenGlにデータを送信しようとしています。Sizeofのおかげで、配列の送信は簡単です。

array := [...]Whatever {lots of data}
array_ptr := gl.Pointer(&array[0])
array_size := gl.Sizeiptr(unsafe.Sizeof(array))
gl.BufferData(gl.ARRAY_BUFFER, array_size, array_ptr, gl.STATIC_DRAW)

コンパイル時に3Dモデルのサイズがわからないため、配列の代わりにスライスを使用したいと思います。

スライスのコンテンツのサイズ(バイト単位)を取得するにはどうすればよいですか? 私はこれについて考えました:

size := uintptr(len(slice)) * unsafe.Sizeof(slice[0])

しかし、それはあまり一般的ではありません。実際、これが機能するためには、スライスの基になるタイプを知る必要があります。これは、配列のすべての要素が同じサイズであると想定しています。

スライス全体をループして、すべての要素のすべてのサイズを追加することもできます。それほど速くはありません。

私は常にlen(s)== cap(s)を維持する準備ができています、それは私を助けることができますか?

編集:ランタイムリフレクションを使用した提案されたソリューションの実装

package main

import "fmt"
import "reflect"

func ElemSize(container interface{}) uintptr {
    return reflect.TypeOf(container).Elem().Size()
}
func ElemSizeVerbose(container interface{}) uintptr {
    t := reflect.TypeOf(container)
    e := t.Elem()
    s := e.Size()
    fmt.Println(t, e, s)
    return s
}
func main() {
    a := [...]int8{2, 3, 5, 7, 11} // Array
    s := []int64{2, 3, 5, 7, 11} // Slice
    z := []int32{} // Even empty things
    ElemSizeVerbose(a) // [5]int8 int8 1
    ElemSizeVerbose(s) // []int64 int64 8
    ElemSizeVerbose(z) // []int32 int32 4
}
4

2 に答える 2

7

スライスまたは配列では、すべての要素が常に同じサイズです。したがって、この例は、len(s) > 0 である限り機能します。つまり、スライスに少なくとも 1 つの要素が含まれている限り、機能します。そうしないと、パニックになります。

スライスに要素を含める必要がないようにするには、次を使用することをお勧めします。

 uintptr(len(s)) * reflect.TypeOf(s).Elem().Size()
于 2013-02-05T01:29:50.817 に答える