当前位置:  开发笔记 > 编程语言 > 正文

将4个整数打包成一个[10,10,10,2]整数

如何解决《将4个整数打包成一个[10,10,10,2]整数》经验,为你挑选了1个好方法。

我正在将一些C++示例移植到Java

我现在卡住尝试将以下布局[10,10,10,2]中的四个整数打包成一个整数,这是第一个int占据前10位,类似于第二个和第三个,而最后一个只是最后两位.

在C++示例中,这是打包它们的代码:

GLM_FUNC_QUALIFIER uint32 packSnorm3x10_1x2(vec4 const & v)
    {
        detail::i10i10i10i2 Result;
        Result.data.x = int(round(clamp(v.x,-1.0f, 1.0f) * 511.f));
        Result.data.y = int(round(clamp(v.y,-1.0f, 1.0f) * 511.f));
        Result.data.z = int(round(clamp(v.z,-1.0f, 1.0f) * 511.f));
        Result.data.w = int(round(clamp(v.w,-1.0f, 1.0f) *   1.f));
        return Result.pack;
    }

Result.data如下struct:

union i10i10i10i2
    {
        struct
        {
            int x : 10;
            int y : 10;
            int z : 10;
            int w : 2;
        } data;
        uint32 pack;
    };

输入等于[-1f,-1f,0f,1f]我们得到Result.data等于[-511,-511,0,1]和返回值1074267649,二进制是:

        0                       -511
   |          |             |          |
 0100 0000 0000 1000 0000 0110 0000 0001
 ||             |          |
 1                  -511

到目前为止我所做的是:

public static int packSnorm3x10_1x2(float[] v) {
    int[] tmp = new int[4];
    tmp[0] = (int) (Math.max(-1, Math.min(1, v[0])) * 511.f);
    tmp[1] = (int) (Math.max(-1, Math.min(1, v[1])) * 511.f);
    tmp[2] = (int) (Math.max(-1, Math.min(1, v[2])) * 511.f);
    tmp[3] = (int) (Math.max(-1, Math.min(1, v[3])) * 1.f);
    int[] left = new int[4];
    left[0] = (tmp[0] << 22);
    left[1] = (tmp[1] << 22);
    left[2] = (tmp[2] << 22);
    left[3] = (tmp[3] << 30);
    int[] right = new int[4];
    right[0] = (left[0] >> 22);
    right[1] = (left[1] >> 12);
    right[2] = (left[2] >> 2);
    right[3] = (left[3] >> 0);
    return right[0] | right[1] | right[2] | right[3];
}

tmp[-511,-511,0,1],left[-2143289344,-2143289344,0,1073741824],二进制是:

[1000 0000 0100 0000 0000 0000 0000 0000,
 1000 0000 0100 0000 0000 0000 0000 0000,
 0000 0000 0000 0000 0000 0000 0000 0000,
 0100 0000 0000 0000 0000 0000 0000 0000]

到目前为止它是有道理的.现在我清理了左边的值,我想把它们拖到右边的右边.但是当我这样做的时候,我得到左边的空白填充了1s,我猜是因为java中的signed int(?).

然后right[-511,-523264,0,1073741824]或:

[1111 1111 1111 1111 1111 1110 0000 0001,
 1111 1111 1111 1000 0000 0100 0000 0000,
 0000 0000 0000 0000 0000 0000 0000 0000,
 0100 0000 0000 0000 0000 0000 0000 0000]

那么,为什么会发生这种情况,我该如何解决这个问题呢?也许仅使用ANDing我感兴趣的位?



1> BlueMoon93..:

无符号右移运算符>>>将零移动到最左侧位置.

资料来源:https://docs.oracle.com/javase/tutorial/java/nutsandbolts/op3.html

推荐阅读
linjiabin43
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有