- Java 双重比较
- java - 比较器与 Apache BeanComparator
- Objective-C 完成 block 导致额外的方法调用?
- database - RESTful URI 是否应该公开数据库主键?
我知道我可以编写以下方法来计算 long 的设置位索引:
private static List<Integer> bitPositions(long number) {
final List<Integer> positions = new ArrayList<>();
int position = 1;
while (number != 0) {
if ((number & 1L) != 0) {
positions.add(position);
}
position++;
number = number >>> 1;
}
return positions;
}
最佳答案
最快的方法
BitBank's answer to this question 的速度大约是这个答案下面的两种方法的两倍。这窃取了 BitBank 答案中的想法,并通过使用位旋转反复关闭最不重要的一位而不是右移一位,使其比我的机器上的速度快 73%(比问题的方法快 9 倍)离开右端并跟踪发生了多少变化。
private static final byte[] bitPositions(long n) {
final byte[] result = new byte[Long.bitCount(n)];
for (int i = 0; n != 0L; i++) {
result[i] = (byte) ((byte) Long.numberOfTrailingZeros(n) + 1);
n &= n - 1L; // Change least-significant one bit to a zero bit.
}
return result;
}
byte
的双重转换稍微加快了速度。我认为这是因为它允许 byte
大小而不是 int
大小的算术。 for (int bitPosition : bitPositions(n)) {
// Do something with `bitPosition`.
}
long temp = n;
while (temp != 0L) {
int bitPosition = Long.numberOfTrailingZeros(temp) + 1;
temp &= temp - 1L; // Change least-significant one bit to a zero bit.
// Do something with `bitPosition`.
}
byte[]
而不是
List<Integer>
中)大约快两倍:
private static final byte[] bitPositions(long n) {
final byte[] result = new byte[Long.bitCount(n)];
int i = 0;
for (byte bit = 1; n != 0L; bit++) {
if ((n & 1L) != 0) result[i++] = bit;
n >>>= 1;
}
return result;
}
byte bit = 1
循环中的
for
更改为
byte bit = 0
以切换到从零而不是从一开始对位位置进行编号的传统方法。
Long.bitCount(n)
预先计算所需的容量(使用处理器的非常快速的“popcount”指令)可以大大加快您的方法。您可以通过使用 ArrayList
制作 new ArrayList<>(Long.bitCount(n))
来更改此设置。 ArrayList<Integer>
比 byte[]
慢,因为:-127
cache 查找低值( 128
到 Integer
)Integer
值以将它们放入 ArrayList
。 int
中的 List<Integer>
时必须浪费时间,因为您必须从 Integer
检索 List<Integer>
,然后从 int
检索 Integer
。 byte[]
使用 ArrayList<Integer>
内存的大约 1/4(32 位系统)或 1/8(64 位系统),因为 byte
比指向 Integer
的指针小得多。 private static final byte[] bitPositions(final long n) {
final byte[] result = new byte[Long.bitCount(n)];
int i = 0;
if ((n & 1L) != 0L) result[i++] = 1;
if ((n & 2L) != 0L) result[i++] = 2;
if ((n & 4L) != 0L) result[i++] = 3;
if ((n & 8L) != 0L) result[i++] = 4;
if ((n & 16L) != 0L) result[i++] = 5;
if ((n & 32L) != 0L) result[i++] = 6;
if ((n & 64L) != 0L) result[i++] = 7;
if ((n & 128L) != 0L) result[i++] = 8;
if ((n & 256L) != 0L) result[i++] = 9;
if ((n & 512L) != 0L) result[i++] = 10;
if ((n & 1024L) != 0L) result[i++] = 11;
if ((n & 2048L) != 0L) result[i++] = 12;
if ((n & 4096L) != 0L) result[i++] = 13;
if ((n & 8192L) != 0L) result[i++] = 14;
if ((n & 16384L) != 0L) result[i++] = 15;
if ((n & 32768L) != 0L) result[i++] = 16;
if ((n & 65536L) != 0L) result[i++] = 17;
if ((n & 131072L) != 0L) result[i++] = 18;
if ((n & 262144L) != 0L) result[i++] = 19;
if ((n & 524288L) != 0L) result[i++] = 20;
if ((n & 1048576L) != 0L) result[i++] = 21;
if ((n & 2097152L) != 0L) result[i++] = 22;
if ((n & 4194304L) != 0L) result[i++] = 23;
if ((n & 8388608L) != 0L) result[i++] = 24;
if ((n & 16777216L) != 0L) result[i++] = 25;
if ((n & 33554432L) != 0L) result[i++] = 26;
if ((n & 67108864L) != 0L) result[i++] = 27;
if ((n & 134217728L) != 0L) result[i++] = 28;
if ((n & 268435456L) != 0L) result[i++] = 29;
if ((n & 536870912L) != 0L) result[i++] = 30;
if ((n & 1073741824L) != 0L) result[i++] = 31;
if ((n & 2147483648L) != 0L) result[i++] = 32;
if ((n & 4294967296L) != 0L) result[i++] = 33;
if ((n & 8589934592L) != 0L) result[i++] = 34;
if ((n & 17179869184L) != 0L) result[i++] = 35;
if ((n & 34359738368L) != 0L) result[i++] = 36;
if ((n & 68719476736L) != 0L) result[i++] = 37;
if ((n & 137438953472L) != 0L) result[i++] = 38;
if ((n & 274877906944L) != 0L) result[i++] = 39;
if ((n & 549755813888L) != 0L) result[i++] = 40;
if ((n & 1099511627776L) != 0L) result[i++] = 41;
if ((n & 2199023255552L) != 0L) result[i++] = 42;
if ((n & 4398046511104L) != 0L) result[i++] = 43;
if ((n & 8796093022208L) != 0L) result[i++] = 44;
if ((n & 17592186044416L) != 0L) result[i++] = 45;
if ((n & 35184372088832L) != 0L) result[i++] = 46;
if ((n & 70368744177664L) != 0L) result[i++] = 47;
if ((n & 140737488355328L) != 0L) result[i++] = 48;
if ((n & 281474976710656L) != 0L) result[i++] = 49;
if ((n & 562949953421312L) != 0L) result[i++] = 50;
if ((n & 1125899906842624L) != 0L) result[i++] = 51;
if ((n & 2251799813685248L) != 0L) result[i++] = 52;
if ((n & 4503599627370496L) != 0L) result[i++] = 53;
if ((n & 9007199254740992L) != 0L) result[i++] = 54;
if ((n & 18014398509481984L) != 0L) result[i++] = 55;
if ((n & 36028797018963968L) != 0L) result[i++] = 56;
if ((n & 72057594037927936L) != 0L) result[i++] = 57;
if ((n & 144115188075855872L) != 0L) result[i++] = 58;
if ((n & 288230376151711744L) != 0L) result[i++] = 59;
if ((n & 576460752303423488L) != 0L) result[i++] = 60;
if ((n & 1152921504606846976L) != 0L) result[i++] = 61;
if ((n & 2305843009213693952L) != 0L) result[i++] = 62;
if ((n & 4611686018427387904L) != 0L) result[i++] = 63;
if ((n & -9223372036854775808L) != 0L) result[i++] = 64;
return result;
}
>>>
的需要。 ++
。 关于java - 长的快速按位运算,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41471134/
为什么 (defun boolimplies (a b) (or (not a) b)) if called as(boolimplies 'a 'b) 返回 B? 即使我不使用任何 boolean
这个问题已经有答案了: Are there builtin functions for elementwise boolean operators over boolean lists? (5 个回答
我正在寻求帮助以使以下功能看起来更清晰。我觉得我可以通过使用更少的代码行来实现同样的目标。 标题看起来一定很困惑,所以让我详细说明一下。我创建了一个函数,它接受用户输入(即 72+5),将字符串拆分为
我正在学习 C++ 并尝试为矩阵编写一个 C++ 类,我在其中将矩阵存储为一维 C 数组。为此,我定义了一个 element成员函数根据矩阵元素在数组中的位置访问矩阵元素。然后我重载了 class
我正在学习 C++ 并尝试为矩阵编写一个 C++ 类,我在其中将矩阵存储为一维 C 数组。为此,我定义了一个 element成员函数根据矩阵元素在数组中的位置访问矩阵元素。然后我重载了 class
伙计们,以下内容不起作用 函数返回 true,变量返回 false,但它不会进入 when 子句。我尝试像这样放大括号 但是当我将变量的值设置为 true 并将上面的代码更改为 它进入w
关闭。此题需要details or clarity 。目前不接受答案。 想要改进这个问题吗?通过 editing this post 添加详细信息并澄清问题. 已关闭 9 年前。 Improve th
我是原生 C 语言的新手,但我没有看到错误。 我尝试在这种情况下使用 if 操作: #define PAGE_A 0 #define PAGE_B 1 int pageID = 0; if (page
我正在从事一个项目,让用户鼠标滚轮移动并知道它向上或向下滚动。在我的代码中,我可以上下移动。但我想将 Action 保存到一个字符串中。例如,如果用户向上向上向下滚动'mhmh' 显示返回“UUD”但
我有一个 MySQL 表 payment我在其中存储客户的所有付款相关数据。表字段为:fileNo , clientName , billNo , billAmount , status 。我想构建一
我的表架构如下: +------+-------+-------+
我有这个(顺便说一句,我刚刚开始学习): #include #include using namespace std; int main() { string mystr; cout << "We
我正在用 bash 构建一个用于 Linux (SLES 11SP3) 的脚本。我想通过使用以下语法查找它的 pid 来检查某个进程是否存在: pid="$(ps -ef | grep -v grep
我有一个包含两列的表格; CREATE TABLE IF NOT EXISTS `QUESTION_CATEGORY_RELATION` ( `question_id` int(16) NOT N
我对 Python 如何计算 bool 语句感到困惑。 例如 False and 2 or 3 返回 3 这是如何评估的?我认为 Python 首先会查看“False and 2”,甚至不查看“or
这个问题在这里已经有了答案: 12 年前关闭。 这可能是非常基本的......但我似乎不明白: 如何 (2 & 1) = 0 (3 & 1) = 1 (4 & 1) = 0 等等.. 上面的这种模式似
无论如何在Haskell中定义如下函数? or True True = True or True undefined = True or True False
如您所知,TCL 有一些数学函数,例如 罪 , 因 , 和 假设 在 中调用的expr 带有 的命令() 大括号如下: puts [expr sin(1.57)] 现在如何使用 TCL 添加功能 li
让我们考虑两个数组列表。 ArrayList list1 = new ArrayList(); list1.add(1); list1.add(2); list1.add(3); ArrayList
我想包含和排除使用AND和OR的专业知识,包括与AND和OR操作正常工作。但是,当将排除专家与AND和OR一起使用时,返回与3相同的结果计数。我使用的是1.4版 Elasticsearch 。帮助我解
我是一名优秀的程序员,十分优秀!