jmu-Java-PTA题解 (6.6 - 集合(泛型)-10-GeneralStack) 网安2312陈卓

问题要求

实现一个通用的栈数据结构 GeneralStack,它能处理任意引用类型的数据。具体需求如下:

  1. 编写 GeneralStack 接口,其操作对任何引用类型的数据都适用。接口定义的方法包括:
    • push(item):若 item 为 null,则不入栈并直接返回 null。
    • pop():出栈操作,若栈为空则返回 null。
    • peek():获取栈顶元素,若栈为空则返回 null。
    • empty():判断栈是否为空,若为空返回 true。
    • size():返回栈中元素的数量。
  2. 定义 GeneralStack 的实现类 ArrayListGeneralStack,内部使用 ArrayList 对象存储元素,属性名为 list。同时,实现 toString() 方法,该方法返回 list.toString()。
  3. 定义 Car 对象,包含私有属性 id 和 name,并使用 Eclipse 自动生成 setter、getter 和 toString 方法。
  4. 在 main 方法中,根据用户输入的选项(quit、Integer、Double、Car)进行相应操作。若输入 quit 则直接退出;否则,输入整数 m 与 n,m 代表入栈个数,n 代表出栈个数。然后根据选项声明不同类型的栈,进行入栈、出栈操作,并按要求输出结果。

输入格式:

  1. 输入选项(quit、Integer、Double、Car)。若输入 quit,程序结束。
  2. 若输入其他选项,接着输入整数 m 和 n。
  3. 输入 m 个相应类型的数据用于入栈。

输出格式:

  1. 根据不同选项,输出测试类型(如 Integer Test、Double Test、Car Test)。
  2. 依次输出入栈和出栈的元素信息。
  3. 输出栈的 toString() 方法结果。
  4. 若选项为 Integer 或 Double,输出栈中剩余元素的累加和;若选项为 Car,输出栈中剩余元素的 name 属性。
  5. 输出栈实现类所实现的接口信息。

输入样例:

Integer
5
2
1 2 3 4 5
Double
5
3
1.1 2.0 4.9 5.7 7.2
Car
3
2
1 Ford
2 Cherry
3 BYD
quit

输出样例:

Integer Test
push:1
push:2
push:3
push:4
push:5
pop:5
pop:4
[1, 2, 3]
sum=6
interface GeneralStack
Double Test
push:1.1
push:2.0
push:4.9
push:5.7
push:7.2
pop:7.2
pop:5.7
pop:4.9
[1.1, 2.0]
sum=3.1
interface GeneralStack
Car Test
push:Car [id=1, name=Ford]
push:Car [id=2, name=Cherry]
push:Car [id=3, name=BYD]
pop:Car [id=3, name=BYD]
pop:Car [id=2, name=Cherry]
[Car [id=1, name=Ford]]
Ford
interface GeneralStack

关键点

  • 泛型接口设计:GeneralStack 接口需使用泛型,以支持不同引用类型的数据。
  • 泛型类实现:ArrayListGeneralStack 类实现 GeneralStack 接口,内部使用 ArrayList 存储元素,避免类型不安全的强制转换。
  • 对象定义:Car 对象需包含必要的属性和方法。
  • 输入处理:main 方法根据用户输入的选项进行不同的操作,包括入栈、出栈和结果输出。

解题步骤

第一步:定义通用栈接口

使用泛型定义 GeneralStack 接口,确保接口中的方法能处理任意引用类型的数据。

interface GeneralStack <T> {
    public T push(T item);
    public T pop();
    public T peek();
    public boolean empty();
    public int size();
    public String toString();
}

第二步:实现通用栈接口

创建 ArrayListGeneralStack 类实现 GeneralStack 接口,内部使用 ArrayList 存储元素。

class ArrayListGeneralStack<T> implements GeneralStack<T> {

    ArrayList<T> list = new ArrayList<>();

    public T push(T item){
        if(item == null){
            return null;
        }
        list.add(item);
        return item;
    }

    public T pop(){
        if(list.isEmpty()){
            return null;
        }
        T e = list.get(list.size()-1);
        list.remove(list.size()-1);
        return e;
    }

    public T peek(){
        if(list.isEmpty()){
            return null;
        }
        T e = list.get(list.size()-1);
        return e;
    }

    public boolean empty(){
        if(list.size() == 0){
            return true;
        }
        return false;
    }

    public int size(){
        return list.size();
    }

    @Override
    public String toString() {
        return list.toString();
    }
}

第三步:定义 Car 类

定义 Car 类,包含 id 和 name 属性,并提供相应的 setter、getter 和 toString 方法。

class Car{
    private int id;
    private String name;

    public Car(int id, String name){
        this.id = id;
        this.name = name;
    }

    public int getId() {
        return id;
    }

    public String getName() {
        return name;
    }

    public void setId(int id) {
        this.id = id;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Car [" +
                "id=" + id +
                ", name=" + name +
                ']';
    }
}

第四步:实现 main 方法

在 main 方法中,根据用户输入的选项进行相应的操作,包括入栈、出栈和结果输出。

import java.util.*;

public class Main {
    public static void main(String[] args){
        Scanner in = new Scanner(System.in);
        while(in.hasNext()){
            String choose = in.next();
            if(choose.equals("quit")){
                break;
            }else{
                int m = in.nextInt();
                int n = in.nextInt();
                ArrayListGeneralStack stack;
                switch (choose){
                    case "Integer":
                        System.out.println("Integer Test");
                        stack = new ArrayListGeneralStack<Integer>();
                        for(int i=0;i<m;i++){
                            System.out.println("push:" + stack.push(in.nextInt()));
                        }
                        for(int i=0;i<n;i++){
                            System.out.println("pop:" + stack.pop());
                        }
                        System.out.println(stack);
                        int sum = 0;
                        int number1 = stack.size();
                        for(int i=0;i<number1;i++){
                            int e = (int) stack.pop();
                            sum = sum + e;
                        }
                        System.out.println("sum=" + sum);
                        System.out.println(stack.getClass().getInterfaces()[0]);
                        break;
                    case "Double":
                        System.out.println("Double Test");
                        stack = new ArrayListGeneralStack<Double>();
                        for(int i=0;i<m;i++){
                            System.out.println("push:" + stack.push(in.nextDouble()));
                        }
                        for(int i=0;i<n;i++){
                            System.out.println("pop:" + stack.pop());
                        }
                        System.out.println(stack);
                        double sums = 0;
                        int number2 = stack.size();
                        for(int i=0;i<number2;i++){
                            double e = (double) stack.pop();
                            sums = sums + e;
                        }
                        System.out.println("sum=" + sums);
                        System.out.println(stack.getClass().getInterfaces()[0]);
                        break;
                    case "Car":
                        System.out.println("Car Test");
                        stack = new ArrayListGeneralStack<Car>();
                        for(int i=0;i<m;i++){
                            Car e = new Car(in.nextInt(), in.next());
                            System.out.println("push:" + stack.push(e));
                        }
                        for(int i=0;i<n;i++){
                            System.out.println("pop:" + stack.pop());
                        }
                        System.out.println(stack);
                        for(int i=0;i<stack.size();i++){
                            Car e = (Car)stack.pop();
                            System.out.println(e.getName());
                        }
                        System.out.println(stack.getClass().getInterfaces()[0]);
                        break;
                }
            }
        }
    }
}

整体流程图:

整体代码:

import java.util.*;

interface GeneralStack <T> {
    public T push(T item);
    public T pop();
    public T peek();
    public boolean empty();
    public int size();
    public String toString();
}

class ArrayListGeneralStack<T> implements GeneralStack<T> {

    ArrayList<T> list = new ArrayList<>();

    public T push(T item){
        if(item == null){
            return null;
        }
        list.add(item);
        return item;
    }

    public T pop(){
        if(list.isEmpty()){
            return null;
        }
        T e = list.get(list.size()-1);
        list.remove(list.size()-1);
        return e;
    }

    public T peek(){
        if(list.isEmpty()){
            return null;
        }
        T e = list.get(list.size()-1);
        return e;
    }

    public boolean empty(){
        if(list.size() == 0){
            return true;
        }
        return false;
    }

    public int size(){
        return list.size();
    }

    @Override
    public String toString() {
        return list.toString();
    }
}

class Car{
    private int id;
    private String name;

    public Car(int id, String name){
        this.id = id;
        this.name = name;
    }

    public int getId() {
        return id;
    }

    public String getName() {
        return name;
    }

    public void setId(int id) {
        this.id = id;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Car [" +
                "id=" + id +
                ", name=" + name +
                ']';
    }
}

public class Main {
    public static void main(String[] args){
        Scanner in = new Scanner(System.in);
        while(in.hasNext()){
            String choose = in.next();
            if(choose.equals("quit")){
                break;
            }else{
                int m = in.nextInt();
                int n = in.nextInt();
                ArrayListGeneralStack stack;
                switch (choose){
                    case "Integer":
                        System.out.println("Integer Test");
                        stack = new ArrayListGeneralStack<Integer>();
                        for(int i=0;i<m;i++){
                            System.out.println("push:" + stack.push(in.nextInt()));
                        }
                        for(int i=0;i<n;i++){
                            System.out.println("pop:" + stack.pop());
                        }
                        System.out.println(stack);
                        int sum = 0;
                        int number1 = stack.size();
                        for(int i=0;i<number1;i++){
                            int e = (int) stack.pop();
                            sum = sum + e;
                        }
                        System.out.println("sum=" + sum);
                        System.out.println(stack.getClass().getInterfaces()[0]);
                        break;
                    case "Double":
                        System.out.println("Double Test");
                        stack = new ArrayListGeneralStack<Double>();
                        for(int i=0;i<m;i++){
                            System.out.println("push:" + stack.push(in.nextDouble()));
                        }
                        for(int i=0;i<n;i++){
                            System.out.println("pop:" + stack.pop());
                        }
                        System.out.println(stack);
                        double sums = 0;
                        int number2 = stack.size();
                        for(int i=0;i<number2;i++){
                            double e = (double) stack.pop();
                            sums = sums + e;
                        }
                        System.out.println("sum=" + sums);
                        System.out.println(stack.getClass().getInterfaces()[0]);
                        break;
                    case "Car":
                        System.out.println("Car Test");
                        stack = new ArrayListGeneralStack<Car>();
                        for(int i=0;i<m;i++){
                            Car e = new Car(in.nextInt(), in.next());
                            System.out.println("push:" + stack.push(e));
                        }
                        for(int i=0;i<n;i++){
                            System.out.println("pop:" + stack.pop());
                        }
                        System.out.println(stack);
                        for(int i=0;i<stack.size();i++){
                            Car e = (Car)stack.pop();
                            System.out.println(e.getName());
                        }
                        System.out.println(stack.getClass().getInterfaces()[0]);
                        break;
                }
            }
        }
    }
}

思考:在实现通用栈时,使用泛型和不使用泛型会有显著的差异。若不使用泛型,要为每种数据类型单独定义栈类,例如为 Integer 类型和 String 类型分别定义栈类,这样做会导致代码冗余,每种数据类型都需要编写一套相似的栈操作代码,增加了代码量和维护成本,同时也会使类型不安全,如果需要处理新的数据类型,必须手动创建新的栈类,容易出错。而使用泛型则方便许多,它只需编写一次栈操作代码,就可以处理各种类型的数据
同时也避免了运行时的类型转换错误。此外该题中也可以使用LinkedList 替代 ArrayList,LinkedList 是动态扩展,使用LinkedList 会使插入和删除效率增高,但其内存开销大,会导致随机访问效率低。该题同样也可以使用栈(stack)处理,其细节方面在此不再给出,感兴趣的人可以尝试一下或者有想法的人欢迎与我讨论。

posted @ 2025-04-14 17:34  取名字比写博客还难  阅读(32)  评论(0)    收藏  举报