You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在控制台并排打印扑克牌?——Crazy Eights项目技术求助

解决控制台并排打印扑克牌 & 关于Deck继承ArrayList的疑问

嘿,我来帮你搞定这两个问题!

一、让扑克牌在控制台并排打印

你现在的问题是每张卡片的face()方法返回的是完整的多行字符串,直接打印会让卡片上下堆叠。要实现并排,我们需要逐行打印多张卡片的对应行,而不是打印完一张再打印另一张。

步骤1:修改Card类,返回卡片的行数组

把原来的face()方法改成返回一个字符串数组,每个元素对应卡片的一行:

class Card {
    private int value = 0;
    private String suit = null;

    public Card(int value, String suit) {
        this.value = value;
        this.suit = suit;
    }

    int getValue() { return value; }
    String getSuit() { return suit; }

    // 返回卡片的每一行字符串
    String[] getFaceLines() {
        String[] lines = new String[8]; // 卡片总共8行:顶边框+6行内容+底边框
        lines[0] = "+-----------+";

        for(int lineIdx = 1; lineIdx <= 6; lineIdx++) {
            StringBuilder lineContent = new StringBuilder("|");
            if(lineIdx == 2) { // 第二行显示牌面数值(优化显示A/J/Q/K)
                String displayValue = switch(value) {
                    case 1 -> "A";
                    case 11 -> "J";
                    case 12 -> "Q";
                    case 13 -> "K";
                    default -> String.valueOf(value);
                };
                // 对齐显示:两位数字(如10)占3位,一位数字前面补空格
                lineContent.append(String.format("%3s", displayValue)).append("       ");
            } else if(lineIdx == 4) { // 第四行显示花色
                String suitText = switch(suit) {
                    case "Clubs" -> "CLUBS";
                    case "Diamonds" -> "DIAMONDS";
                    case "Hearts" -> "HEARTS";
                    case "Spades" -> "SPADES";
                    default -> "";
                };
                // 补空格保证每行内容长度一致
                lineContent.append(" ").append(suitText).append(" ".repeat(9 - suitText.length()));
            } else {
                // 空行填充11个空格
                lineContent.append("           ");
            }
            lineContent.append("|");
            lines[lineIdx] = lineContent.toString();
        }

        lines[7] = "+-----------+";
        return lines;
    }
}

步骤2:修改Deck类,逐行拼接打印多张卡片

在shuffle()方法中,获取多张卡片的行数组,然后逐行拼接打印:

class Deck extends ArrayList<Card> {
    private String[] suits = {"Clubs", "Diamonds", "Hearts", "Spades"};
    private String[] ranks = {"2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "1"};

    public Deck() {
        for (int i = 0; i < ranks.length; i++) {
            for (int j = 0; j < suits.length; j++) {
                this.add(new Card(Integer.parseInt(ranks[i]), suits[j]));
            }
        }
    }

    void shuffle() {
        Random random = new Random();
        for (int i = 0; i < 52 - 1; i++) {
            int randomValue = i + random.nextInt(52 - i);
            Card card = this.get(i);
            this.set(i, this.get(randomValue));
            this.set(randomValue, card);
        }

        // 打印两张并排的卡片
        Card card1 = this.get(0);
        Card card2 = this.get(1);
        String[] card1Lines = card1.getFaceLines();
        String[] card2Lines = card2.getFaceLines();

        // 逐行拼接两张卡片的对应行
        for(int i = 0; i < card1Lines.length; i++) {
            System.out.println(card1Lines[i] + " " + card2Lines[i]);
        }
    }
}

这样打印出来的效果就会是两张卡片并排啦:

+-----------+ +-----------+
|  A        | |  10       |
|           | |           |
| CLUBS     | | SPADES    |
|           | |           |
|           | |           |
|           | |           |
+-----------+ +-----------+

二、关于Deck继承ArrayList的疑问

其实在实际开发中,更推荐用组合而非继承——也就是Deck类里定义一个private ArrayList<Card> cards;成员变量,然后封装add、get等方法,而不是直接继承ArrayList。

不过你的老师要求继承,大概率是为了简化高中阶段的学习:

  • 继承后,Deck直接拥有ArrayList的所有方法(比如add()、get()、set()),不用你自己再写封装代码
  • 可以让你更专注于Deck的核心逻辑(初始化52张牌、洗牌),而不是集合操作的细节

但要明白:这种设计在专业项目中并不合适,因为Deck本质上"不是"ArrayList的一种,继承会暴露很多不必要的方法(比如clear()),违反了面向对象的里氏替换原则。不过作为高中项目,按老师的要求做就好啦~

内容的提问来源于stack exchange,提问作者Bert Hanz

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.29 07:37:21