惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

博客园_首页
Security Archives - TechRepublic
Security Archives - TechRepublic
Application and Cybersecurity Blog
Application and Cybersecurity Blog
cs.CV updates on arXiv.org
cs.CV updates on arXiv.org
C
CERT Recently Published Vulnerability Notes
S
Security @ Cisco Blogs
S
Security Affairs
D
Darknet – Hacking Tools, Hacker News & Cyber Security
L
Lohrmann on Cybersecurity
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
Hacker News: Ask HN
Hacker News: Ask HN
Forbes - Security
Forbes - Security
H
Heimdal Security Blog
A
Arctic Wolf
NISL@THU
NISL@THU
P
Proofpoint News Feed
W
WeLiveSecurity
S
Schneier on Security
AI
AI
Schneier on Security
Schneier on Security
N
News and Events Feed by Topic
L
LINUX DO - 最新话题
Cisco Talos Blog
Cisco Talos Blog
AWS News Blog
AWS News Blog
Hacker News - Newest:
Hacker News - Newest: "LLM"
Know Your Adversary
Know Your Adversary
Scott Helme
Scott Helme
V
Vulnerabilities – Threatpost
Cyberwarzone
Cyberwarzone
I
Intezer
S
Securelist
Help Net Security
Help Net Security
Microsoft Security Blog
Microsoft Security Blog
量子位
让小产品的独立变现更简单 - ezindie.com
让小产品的独立变现更简单 - ezindie.com
小众软件
小众软件
Last Week in AI
Last Week in AI
Jina AI
Jina AI
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
WordPress大学
WordPress大学
罗磊的独立博客
月光博客
月光博客
雷峰网
雷峰网
A
About on SuperTechFans
The GitHub Blog
The GitHub Blog
T
The Blog of Author Tim Ferriss
MongoDB | Blog
MongoDB | Blog
大猫的无限游戏
大猫的无限游戏
博客园 - 司徒正美
CTFtime.org: upcoming CTF events
CTFtime.org: upcoming CTF events

博客园 - 小纸条

模型微调 ruoyiai 启动指南 反向传播 numpy的使用 B 和 B+树 红黑树 ruoyi-vue 梯度下降法 博弈论 离散化 AcWing 907. 区间覆盖 AcWing 906. 区间分组 AcWing 908 最大不相交区间数量 AcWing 905. 区间选点 AcWing 104. 货仓选址 动态规划经典题 窗口函数 1226. 哲学家进餐 1195. 交替打印字符串 1117. H2O 生成 关联子查询
1116. 打印零与奇偶数
小纸条 · 2025-10-28 · via 博客园 - 小纸条

1116. 打印零与奇偶数

题目描述

假设有这么一个类:

class ZeroEvenOdd {
  public ZeroEvenOdd(int n) { ... }      // 构造函数
  public void zero(printNumber) { ... }  // 仅打印出 0
  public void even(printNumber) { ... }  // 仅打印出 偶数
  public void odd(printNumber) { ... }   // 仅打印出 奇数
}

相同的一个 ZeroEvenOdd 类实例将会传递给三个不同的线程:

  1. 线程 A 将调用 zero(),它只输出 0 。
  2. 线程 B 将调用 even(),它只输出偶数。
  3. 线程 C 将调用 odd(),它只输出奇数。

每个线程都有一个 printNumber 方法来输出一个整数。请修改给出的代码以输出整数序列 010203040506... ,其中序列的长度必须为 2n

示例 1:

输入:n = 2
输出:"0102"
说明:三条线程异步执行,其中一个调用 zero(),另一个线程调用 even(),最后一个线程调用odd()。正确的输出为 "0102"。

示例 2:

输入:n = 5
输出:"0102030405"

解法

题目要求交替打印,先打印0,再打印偶数,最后打印奇数。一共打印2*n个数字。

Java

import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

class ZeroEvenOdd {
    private int n;
    private int state = 0; // 0: print zero, 1: print odd, 2: print even
    private ReentrantLock lock = new ReentrantLock();
    private Condition zeroCondition = lock.newCondition();
    private Condition evenCondition = lock.newCondition();
    private Condition oddCondition = lock.newCondition();

    public ZeroEvenOdd(int n) {
        this.n = n;
    }

    // printNumber.accept(x) outputs "x", where x is an integer.
    public void zero(IntConsumer printNumber) throws InterruptedException {
        for (int i = 0; i < n; i++) {
            lock.lock();
            try {
                while (state != 0) {
                    zeroCondition.await();
                }
                printNumber.accept(0);
                if ((i + 1) % 2 == 1) {
                    state = 1; // next print odd
                    oddCondition.signal();
                } else {
                    state = 2; // next print even
                    evenCondition.signal();
                }
            } finally {
                lock.unlock();
            }
        }
    }

    public void even(IntConsumer printNumber) throws InterruptedException {
        for (int i = 2; i <= n; i += 2) {
            lock.lock();
            try {
                while (state != 2) {
                    evenCondition.await();
                }
                printNumber.accept(i);
                state = 0; // next print zero
                zeroCondition.signal();
            } finally {
                lock.unlock();
            }
        }
    }

    public void odd(IntConsumer printNumber) throws InterruptedException {
        for (int i = 1; i <= n; i += 2) {
            lock.lock();
            try {
                while (state != 1) {
                    oddCondition.await();
                }
                printNumber.accept(i);
                state = 0; // next print zero
                zeroCondition.signal();
            } finally {
                lock.unlock();
            }
        }
    }
}

Java

class ZeroEvenOdd {
    private int n;
    private int state = 0; // 0: print zero, 1: print odd, 2: print even

    public ZeroEvenOdd(int n) {
        this.n = n;
    }

    // printNumber.accept(x) outputs "x", where x is an integer.
    public void zero(IntConsumer printNumber) throws InterruptedException {
        for (int i = 0; i < n; i++) {
            synchronized (this) {
                while (state != 0) {
                    this.wait();
                }
                printNumber.accept(0);
                if ((i + 1) % 2 == 1) {
                    state = 1; // next print odd
                } else {
                    state = 2; // next print even
                }
                this.notifyAll();
            }
        }
    }

    public void even(IntConsumer printNumber) throws InterruptedException {
        for (int i = 2; i <= n; i += 2) {
            synchronized (this) {
                while (state != 2) {
                    this.wait();
                }
                printNumber.accept(i);
                state = 0; // next print zero
                this.notifyAll();
            }
        }
    }

    public void odd(IntConsumer printNumber) throws InterruptedException {
        for (int i = 1; i <= n; i += 2) {
            synchronized (this) {
                while (state != 1) {
                    this.wait();
                }
                printNumber.accept(i);
                state = 0; // next print zero
                this.notifyAll();
            }
        }
    }
}

...