java的BitSet位集

本文介绍了如何使用Java的BitSet类实现埃拉托斯特尼筛选法计算2到2000000之间的素数,展示了代码实现过程,并给出了14893363毫秒的运行时间。

2024.1.3 java的BitSet位集

目的: 计算2-2000000之间的素数

import java.util.BitSet;

/**
 1. @author HK
 */
public class Sieve {
    public static void main(String[] args) {
        int n = 2000000;
        long start = System.currentTimeMillis();
        BitSet bitSet = new BitSet(n + 1);
        int count = 0;
        int i;
        for (i = 2; i <= n; i++) {
            bitSet.set(i);
        }
        i = 2;
        while (i * i <= n) {
            if (bitSet.get(i)) {
                count++;
                int k = 2 * i;
                while (k <= n) {
                    bitSet.clear(k);
                    k += i;
                }
            }
            i++;
        }
        while (i <= n) {
            if (bitSet.get(i)){ count++;}
            i++;
        }
        long end=System.currentTimeMillis();
        System.out.println(count+"素数");
        System.out.println((end-start)+"毫秒");
    }
}

采用的是埃拉托斯特尼筛选法计算法:有兴趣可以自己看看

1.创建一个bitSet对象默认为每个位为0
2. set(i)方法将该位上改为1
3. get(i)方法获取当前状态1为true 0为false
4. clear(k)方法将该位上改为0

输出结果:
148933
63毫秒

### Java BitSet 类及其使用方法 #### 什么是 BitSet? `BitSet` 是 Java 中的一个类,于 `java.util` 包下。它提供了一种高效的方式来表示一组布尔值(0 或 1),并允许对其进行各种操作。与普通的布尔数组相比,`BitSet` 更加节省内存,并支持动态扩展[^1]。 #### 如何创建 BitSet 对象? 可以通过两种方式来创建 `BitSet` 实例: 1. **无参构造函数**:默认情况下,初始容量为零,但可以根据需要自动增长。 2. **指定初始大小的构造函数**:可以预先定义一个初始大小,虽然实际分配的空间可能会被调整为最接近该大小的 64 的倍数[^3]。 ```java // 创建一个空的 BitSet BitSet bitSet1 = new BitSet(); // 创建具有特定长度的 BitSet int initialSize = 10; BitSet bitSet2 = new BitSet(initialSize); ``` #### 基本操作 以下是常见的 `BitSet` 操作: 1. **设置某一** 可以通过调用 `set(int index)` 方法将某个置上的比特设为 true (1),或者使用 `clear(int index)` 将其重置为 false (0)[^2]。 ```java bitSet2.set(5); // 设置第 5 为 true bitSet2.clear(7); // 清除第 7 至 false ``` 2. **获取某一的状态** 调用 `get(int index)` 来查询某一置是否为 true。 ```java boolean isSet = bitSet2.get(5); // 返回 true 如果第 5 已被设置 ``` 3. **翻转某一** 使用 `flip(int index)` 方法可改变目标的状态——如果是 true 则变为 false,反之亦然。 ```java bitSet2.flip(5); // 翻转第 5 ``` 4. **逻辑运算** 支持与其他 `BitSet` 进行按 AND (`and`)、OR (`or`) 和 XOR (`xor`) 操作。 ```java BitSet bitSetA = new BitSet(); BitSet bitSetB = new BitSet(); bitSetA.set(1, 3); // 设定 bits at indices 1 and 2 to be set. bitSetB.set(2, 4); // Set bits at indices 2 and 3. bitSetA.and(bitSetB); // 结果只保留两者都为true的置 System.out.println(bitSetA.toString()); // 输出 "[2]" bitSetA.or(bitSetB); // 合并两个合的结果 System.out.println(bitSetA.toString()); // 输出 "[2, 3]" bitSetA.xor(bitSetB); // 不同则为真 System.out.println(bitSetA.toString()); // 输出 "[3]" ``` #### 高效性和适用场景 由于内部实现了基于 long 数组的数据结构优化,因此对于大规模稀疏数据来说非常有效率。此外,在涉及大量标志管理的应用场合尤为合适,例如网络协议状态跟踪或是大型矩阵计算等领域都可以见到它的身影[^3]。 ### 示例代码展示如何利用 BitSet 解决实际问题 下面给出一段完整的例子演示怎样运用 BitSet 完成简单的筛选功能: ```java public class Main { public static void main(String[] args) { int maxNumber = 30; // 初始化一个足够大的 BitSet 表示所有的自然数直到最大数值为止 BitSet primeCandidates = new BitSet(maxNumber + 1); // 默认全部标记为可能素数(true),除了小于2的部分外 primeCandidates.set(2, maxNumber + 1); for (int i = 2; i * i <= maxNumber; ++i){ if(primeCandidates.get(i)){ // 把当前数字的所有倍数排除掉 for(int j=i*i ;j<=maxNumber;j+=i){ primeCandidates.clear(j); } } } // 打印剩余下来的可能是质数的那些编号出来看看效果吧~ System.out.print("Primes up to "+maxNumber+": "); for(int k=primeCandidates.nextSetBit(2);k>=0;k=primeCandidates.nextSetBit(k+1)){ System.out.print(k+" "); } } } ``` 此程序采用埃拉托斯特尼筛法找出给定范围内的所有素数。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值