【沈阳航空航天大学】 <C++ 多态与泛型计分作业>

选择排序函数模板SortArray

【问题描述】采用模板技术定义选择排序函数模板SortArray

【输入形式】一系列数字
【输出形式】排序后的数字

【样例输入】3 2 1 4 5 6 7 8 9 10
【样例输出】1 2 3 4 5 6 7 8 9 10

#include <iostream>
using namespace std;
const int MAX_SIZE = 10;

// 函数模板SortArray,用于选择排序
template <typename T>
void SortArray(T arr[], int size)
{
    for (int i = 0; i < size - 1; i++)
    {
        int minIndex = i;
        for (int j = i + 1; j < size; j++)
        {
            if (arr[j] < arr[minIndex])
            {
                minIndex = j;
            }
        }
        if (minIndex != i)
        {
            temp = arr[i];
            arr[i] = arr[minIndex];
            arr[minIndex] = temp;
        }
    }
}

int main()
{
    int ar[MAX_SIZE];
    for (int i = 0; i < MAX_SIZE; i++)
        cin >> ar[i];

    SortArray<int>(ar, MAX_SIZE);
    cout << ar[0];
    for (int i = 1; i < MAX_SIZE; i++)
        cout << " " << ar[i];
    cout << endl;
    return 0;
}

堆栈类模板程序

【问题描述】将堆栈设计成一个类模板,在堆栈中可以存放任意类型的数据。要求成员函数至少包含构造函数,析构函数,出栈函数pop,入栈函数push(),堆栈为空判断函数IsEmpty()和堆栈为满判断函数IsFull();成员数据至少包括一个指针变量用以保存堆栈数据。

【输入形式】输入一组字符数据和一组整型数据用以验证堆栈功能。
【输出形式】按照样例输出格式进行输出。

【样例输入】
w95oI
43 30 90 15 21 43 99 3 55 9

【样例输出】
int stack full!
int stack full!
I o 5 9 w
3 99 43 21 15 90 30 43

#include <iostream>
using namespace std;

template <typename T>
class Stack
{
private:
    T *space;
    int maxSize;
    int top;

public:
    Stack(int size)
    {
        maxSize = size;
        top = -1;
        space = new T[maxSize];
    }

    ~Stack()
    {
        delete[] space;
    }

    bool push(T data)
    {
        if (IsFull())
        {
            return false;
        }
        space[++top] = data;
        return true;
    }

    T pop()
    {
        if (IsEmpty())
        {
            // 这里可以抛出一个异常
            throw "Stack is empty!";
        }
        return space[top--];
    }

    bool IsEmpty()
    {
        return top == -1;
    }

    bool IsFull()
    {
        return top == maxSize - 1;
    }
};

int main()
{
    char ch;
    Stack<char> s1(5);
    Stack<int> s2(8);
    int i, n;

    for (i = 0; i < 5; i++)
    {
        cin >> ch;
        s1.push(ch);
    }

    for (i = 0; i < 10; i++)
    {
        cin >> n;
        if (!s2.push(n))
            cout << "int stack full!" << endl;
    }

    while (!s1.IsEmpty())
        cout << s1.pop() << ' ';
    cout << endl;

    while (!s2.IsEmpty())
        cout << s2.pop() << ' ';
    cout << endl;

    return 0;
}

顺序表模板类

【问题描述】根据声明的顺序表的模板类,编程实现指定功能,具体功能见代码注释部分。

【输入形式】输入字符数据和整型数据验证模板类
【输出形式】输出插入删除操作后的最终的顺序表

【样例输入】
a b c d
2 x
1
1 2 3 4
1 100
2

【样例输出】
a x c d
4 100 2 1

#include <iostream>

using namespace std;

// 声明顺序表模板类
template <typename Type>
class SqList
{
public:
    SqList(int n);                     // 构造函数,开辟n个顺序表空间
    ~SqList();                         // 析构函数,释放开辟的空间
    bool isEmpty();                    // 空表判断
    void displayList();                // 依次输出顺序表元素,空格分隔
    void insert(int index, Type elem); // 在指定的索引的位置插入元素
    void deleteList(int index);        // 删除指定索引位置的元素

private:
    Type *pelem;
    int length; // 表中实际存储的数据元素的数量
};

// 实现顺序表模板类成员函数
template <typename Type>
SqList<Type>::SqList(int n)
{
    pelem = new Type[n];
    length = 0;
}

template <typename Type>
SqList<Type>::~SqList()
{
    delete[] pelem;
}

template <typename Type>
bool SqList<Type>::isEmpty()
{
    return length == 0;
}

template <typename Type>
void SqList<Type>::displayList()
{
    for (int i = 0; i < length; i++)
    {
        cout << pelem[i] << ' ';
    }
    cout << endl;
}

template <typename Type>
void SqList<Type>::insert(int index, Type elem)
{
    if (index < 0 || index > length)
    {
        cout << "Insert failed! Index out of range." << endl;
        return;
    }
    // 注意:这里没有检查是否已满,因为数组大小在构造函数中已固定
    for (int i = length; i > index; i--)
    {
        pelem[i] = pelem[i - 1];
    }
    pelem[index] = elem;
    length++;
}

template <typename Type>
void SqList<Type>::deleteList(int index)
{
    if (index < 0 || index >= length)
    {
        cout << "Delete failed! Index out of range." << endl;
        return;
    }
    for (int i = index; i < length - 1; i++)
    {
        pelem[i] = pelem[i + 1];
    }
    length--;
}
int main()
{
    int i, n, index;
    char ch;

    SqList<char> sc(10);

    for (i = 0; i < 4; i++)
    { // 添加4个字符到顺序表
        cin >> ch;
        sc.insert(i, ch);
    }
    cin >> index >> ch; // 读取插入位置和插入的字符
    sc.insert(index, ch);
    cin >> index; // 读取删除的位置
    sc.deleteList(index);

    SqList<int> si(5);

    for (i = 0; i < 4; i++)
    { // 添加4个整数到顺序表
        cin >> n;
        si.insert(0, n); // 注意:这里总是插入到表头,如果要根据index插入需要修改逻辑
    }
    cin >> index >> n; // 读取插入位置和插入的整数
    si.insert(index, n);
    cin >> index; // 读取删除的位置
    si.deleteList(index);

    sc.displayList();
    si.displayList();

    return 0;
}

图形类、点类、和圆类编程

【问题描述】已知图形类Shape是一个表示图形的抽象类,Area( )为求图形面积的函数,Perimeter( )为求图形周长的函数,Print()为 输出图形的基本信息。分别设计图形类(Shape)、点类(Point)和圆类(Circle),要求根据如下已知代码,实现相关类。

【输入形式】按序输入三个整型数,分别为圆心横坐标、圆心纵坐标、和半径
【输出形式】按样例输出格式输出相关数据

【样例输入】2 4 5

【样例输出】
x=2,y=4
Area=0
Perimeter=0
x=2,y=4,r=5
Area=78.5398
Perimeter=31.4159

【样例说明】输出时行与行之间无空行,小数点输出多少位编程时不需要理会。

#include <iostream>

using namespace std;

const double PI = 3.1415926;

// 在此补全图形类(Shape)、点类(Point)和圆类(Circle)的相关代码
class Shape
{
public:
    virtual double Area() const = 0;
    virtual double Perimeter() const = 0;
    virtual void Print() const = 0;
};

class Point : public Shape
{
private:
    int x, y;

public:
    Point(int x, int y) : x(x), y(y) {}

    double Area() const override { return 0; }
    double Perimeter() const override { return 0; }

    void Print() const override
    {
        cout << "x=" << x << ",y=" << y;
    }
};

class Circle : public Shape
{
private:
    Point center;
    double radius;

public:
    Circle(int x, int y, double r) : center(x, y), radius(r) {}

    double Area() const override
    {
        return PI * radius * radius;
    }

    double Perimeter() const override
    {
        return 2 * PI * radius;
    }

    void Print() const override
    {
        center.Print();
        cout << "," << "r=" << radius << endl;
    }
};

void fun(Shape &ref)
{
    ref.Print();
    cout << endl;
    cout << "Area=" << ref.Area() << endl;
    cout << "Perimeter=" << ref.Perimeter() << endl;
}

int main()
{
    int x, y, r;

    cin >> x >> y >> r;

    Point p(x, y);
    Circle c(x, y, r);

    fun(p);
    fun(c);

    return 0;
}

抽象类和多态

【问题描述】画面设计公司,设计彩色图形,不同形状、不同颜色图形,需要统计红,蓝两种颜色的使用面积,以便购买绘制涂料。请设计图形类Figure,有color属性,求面积函数,返回颜色函数;定义子类矩形类,定义子类椭圆类。请用纯虚函数,多态实现。其中,PI用3.14,其他数值型用double,最后输出保留2位小数。

【输入形式】椭圆的数目
椭圆的短半轴,长半轴,颜色

矩形的数目
矩形的长,宽,颜色

【输出形式】每种颜色的面积

【样例输入】
2
3,4,r
5,6,b
3
6,7,r
8,9,r
4,7,b

【样例输出】
red area:151.68
blue area:122.20

#include <iostream>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
using namespace std;

class Figure
{ // 图形抽象类
protected:
    char color[10];

public:
    virtual double getArea() = 0;
    virtual const char *getColor() = 0;
    virtual ~Figure() {}
};
class Ellipse : public Figure
{ // 椭圆类
private:
    double a;
    double b;

public:
    Ellipse(double a, double b, const char *color) : a(a), b(b)
    {
        strcpy(this->color, color);
    }
    double getArea() override
    {
        return 3.14 * a * b;
    }
    const char *getColor() override
    {
        return this->color;
    }
};
class Rectangle : public Figure
{ // 矩形类
private:
    double length;
    double width;

public:
    Rectangle(double length, double width, const char *color) : length(length), width(width)
    {
        strcpy(this->color, color);
    }
    double getArea() override
    {
        return length * width;
    }
    const char *getColor() override
    {
        return this->color;
    }
};
int main()
{
    int n;
    cin >> n;                         // 输入椭圆的数目
    double redArea = 0, blueArea = 0; // 初始化红蓝色面积
    for (int i = 0; i < n; ++i)
    {
        double a, b;
        char color[10];
        scanf("%lf,%lf,%s", &a, &b, color);
        Ellipse ellipse(a, b, color); // 创建椭圆对象
        if (strcmp(ellipse.getColor(), "r") == 0)
        {
            redArea += ellipse.getArea(); // 累加红色面积
        }
        else if (strcmp(ellipse.getColor(), "b") == 0)
        {
            blueArea += ellipse.getArea(); // 累加蓝色面积
        }
    }

    cin >> n; // 输入矩形的数目
    for (int i = 0; i < n; ++i)
    {
        double length, width;
        char color[10];
        scanf("%lf,%lf,%s", &length, &width, color); // 输入矩形的长,宽,颜色
        Rectangle rectangle(length, width, color);   // 创建矩形对象
        if (strcmp(rectangle.getColor(), "r") == 0)
        {
            redArea += rectangle.getArea(); // 累加红色面积
        }
        else if (strcmp(rectangle.getColor(), "b") == 0)
        {
            blueArea += rectangle.getArea(); // 累加蓝色面积
        }
    }

    printf("red area:%.2lf\nblue area:%.2lf\n", redArea, blueArea); // 输出结果
    return 0;
}

定义一个能够存储任何对象的链表类

【问题描述】采用模板技术定义一个能够存储任何对象的链表类,能够从键盘读入存储的数据类型、数据个数和数据列表,并按照输入顺序输出数据列表。
说明:
(1)0代表整型int; 1代表浮点型float 2代表字符串类型string.
(2)输入字符串类型时,可直接使用C++标准类库中的string类型。
(3)输入数据类型 不是 0,1,2三种时,输出error。

【输入形式】
数据类型 数据格式 数组元素
【输出形式】
数组元素 (浮点数保留一位小数)

【样例输入】
13
1 2 3
【样例输出】
1.0 2.0 3.0

【样例输入】
2 3
sam jake love
【样例输出】
sam jake love

【样例输入】
5 3
sam jake love
【样例输出】
error

#include <iostream>
#include <string.h>
#include <stdio.h>
using namespace std;

// 链表类的前向声明
template <class T>
class list;
template <class T> // 声明模板
class node
{                  // 定义结构模板
    T val;         // val取任意类型,即模板参数类型
    node<T> *next; // 此处node为结构模板
public:
    node()
    {
        next = NULL;
    }
    node(T a)
    {
        val = a;
        next = NULL;
    }

    friend class list<T>;
};

// 请完成链表类的设计
template <class T>
class list
{
private:
    node<T> *head;

public:
    list()
    {
        head = NULL;
    }

    void insert(T val)
    {
        if (head == NULL)
        {
            head = new node<T>(val);
        }
        else
        {
            node<T> *current = head;
            while (current->next != NULL)
            {
                current = current->next;
            }
            current->next = new node<T>(val);
        }
    }

    void print()
    {
        node<T> *current = head;
        while (current != NULL)
        {
            if (typeid(T) == typeid(int))
            {
                cout << current->val << " ";
            }
            else if (typeid(T) == typeid(float))
            {
                cout.setf(ios::fixed);
                cout.precision(1);
                cout << current->val << " ";
            }
            else if (typeid(T) == typeid(string))
            {
                cout << current->val << " ";
            }
            else
            {
                cout << "error";
                return;
            }
            current = current->next;
        }
        cout << endl;
    }
};

int main()
{
    int kind = 0; // 0:表示整型,1:单精度浮点数, 2:字符串
    int cnt = 0;
    cin >> kind >> cnt;

    // 整数链表
    if (kind == 0)
    {
        list<int> intlist;
        int nTemp = 0;
        for (int i = 0; i < cnt; i++)
        {
            cin >> nTemp;
            intlist.insert(nTemp);
        }
        intlist.print();
    }

    // 浮点数链表
    else if (kind == 1)
    {
        list<float> floatlist;
        float fTemp = 0;
        cout.setf(ios::fixed);
        cout.precision(1);
        for (int i = 0; i < cnt; i++)
        {
            cin >> fTemp;
            floatlist.insert(fTemp);
        }
        floatlist.print();
    }

    // 字符串链表
    else if (kind == 2)
    {
        list<string> charlist;
        char temp[100];
        for (int i = 0; i < cnt; i++)
        {
            cin >> temp;
            charlist.insert(temp);
        }
        charlist.print();
    }
    else
        cout << "error";

    return 0;
}

二维点Point对象的数组类 PointArray

【问题描述】
设计数组类 PointArray,用以存放例题中定义的Point类对象。
要求如下:
(1) 私有成员Point *pData,存放点类对象,size表示数组长度;
(2) 通过构造函数PointArray(int size)为数组分配空间;
(3) 通过析构函数,用以释放数组空间;
(4) 设计拷贝构造函数,用以数组复制;

【输入形式】
数组长度
x坐标 y坐标
【输出形式】
正序输出每个点的坐标
逆序输出每个点的坐标

【样例输入】
5
1 2
2 3
3 4
4 5
5 6
【样例输出】
元素:0的坐标为:x=1,y=2
元素:1的坐标为:x=2,y=3
元素:2的坐标为:x=3,y=4
元素:3的坐标为:x=4,y=5
元素:4的坐标为:x=5,y=6
倒序输出:
x=5,y=6
x=4,y=5
x=3,y=4
x=2,y=3
x=1,y=2

#include <iostream>
using namespace std;
class PointArray; // 前向声明

class Point
{
    int x, y;

public:
    // Point类的构造函数
    Point(int x = 0, int y = 0) : x(x), y(y) {}
    void SetX(int x) { this->x = x; }
    void SetY(int y) { this->y = y; }
    int GetX() { return x; }
    int GetY() { return y; }

    // 将PointArray声明为Point类的友元类
    friend class PointArray;

    // 通过友元方式重载输出运算符
    friend ostream &operator<<(ostream &out, Point &pnt);
};

// 输出运算符重载
ostream &operator<<(ostream &out, Point &pnt)
{
    cout << "x=" << pnt.x << ",y=" << pnt.y;
    return cout;
}

class PointArray
{
    Point *pData;
    int size;

public:
    explicit PointArray(int size);
    ~PointArray();

    PointArray(const PointArray &src);                // 拷贝构造函数
    PointArray(PointArray &&src);                     // 移动构造函数
    Point &operator[](int idx);                       // 重载下标运算符
    PointArray &operator=(const PointArray &src);     // 重载赋值运算符
    PointArray &operator=(PointArray &&src) noexcept; // 移动赋值运算符

    void Print(); // 打印函数
};

// 普通构造函数
PointArray::PointArray(int size)
{
    this->size = size;
    pData = new Point[size];
}
// 析构函数
PointArray::~PointArray()
{
    delete[] pData;
}
// 拷贝构造函数
PointArray::PointArray(const PointArray &src)
{
    size = src.size;
    pData = new Point[src.size];
    for (int i = 0; i < size; ++i)
    {
        pData[i] = src.pData[i];
    }
}

// 移动构造函数
PointArray::PointArray(PointArray &&src)
{
    pData = src.pData;
    size = src.size;
    src.pData = NULL;
    src.size = 0;
}

// 重载下标运算符
Point &PointArray::operator[](int idx)
{
    return pData[idx];
}

// 重载赋值运算符
PointArray &PointArray::operator=(const PointArray &src)
{
    if (this != &src)
    {
        delete[] pData;
        size = src.size;
        pData = new Point[src.size];
        for (int i = 0; i < size; ++i)
        {
            pData[i] = src.pData[i];
        }
    }
    return *this;
}

// 移动赋值运算符
PointArray &PointArray::operator=(PointArray &&src) noexcept
{
    if (this == &src)
        return *this;

    size = src.size;
    if (this->pData != nullptr)
        delete[] pData;
    pData = src.pData;

    src.pData = nullptr;
    src.size = 0;

    return *this;
}

void PointArray::Print()
{
    if (size <= 0)
    {
        cout << "元素个数为0!" << endl;
        return;
    }

    for (int i = 0; i < size; i++)
    {
        cout << "元素:" << i << "的坐标为:x=" << pData[i].x << ",y=" << pData[i].y << endl;
    }
}

int main()
{
    int count = 0;
    cin >> count;

    PointArray ar(count);
    PointArray br(12);

    int x, y;
    for (int i = 0; i < count; i++)
    {
        cin >> x >> y;
        ar[i].SetX(x);
        ar[i].SetY(y);
    }

    // 输出数组元素
    ar.Print();

    br = ar;
    if (count > 0)
    {
        cout << "倒序输出:" << endl;

        for (int i = count - 1; i >= 0; i--)
            cout << br[i] << endl;
    }
}

Dog类和Cat类分别继承Animal类

【问题描述】Dog类和Cat类分别继承Animal类;
Animal类、Dog类和Cat类各有一个默认构造函数,分别输出字符串“Animal”,“Dog” 和“Cat”;一个析构函数;
在类中添加静态数据成员,用于运行时计算所有Animal,Dog和Cat类对象的数量;
在各类中添加静态函数成员getcount()函数,用于分别显示Animal,Dog和Cat类对象的数量;
在 Animal 类中定义纯虚函数 speak();在 Dog 和 Cat类中覆盖基类的 speak() 函数。
Dog类的speak函数输出字符串“wang”;Cat类的speak函数输出字符串“miao”。
主函数中,输入Dog数量n,Cat数量m;生成相关动物对象,显示数量变化情况;

【输入形式】输入Dog数量n,Cat数量m
【输出形式】生成相关动物对象,显示数量变化情况

【样例输入】
3
4
【样例输出】
Animal
Dog
Animal
Dog
Animal
Dog
Animal:3
Dog:3
Animal
Cat
Animal
Cat
Animal
Cat
Animal
Cat
Animal:7
Cat:4
wang
wang
wang
miao
Animal:3
Dog:0
Cat:3

#include <iostream>
#include <stdio.h>
#include <stdlib.h>
using namespace std;

class Animal
{
protected:
    static int count;

public:
    Animal()
    {
        cout << "Animal" << endl;
        count++;
    }
    virtual ~Animal()
    {
        count--;
    }
    static void getcount()
    {
        cout << "Animal:" << count << endl;
    }
    virtual void speak() = 0;
};

int Animal::count = 0;

class Dog : public Animal
{
protected:
    static int count;

public:
    Dog()
    {
        cout << "Dog" << endl;
        count++;
    }
    ~Dog()
    {
        count--;
    }
    static void getcount()
    {
        cout << "Dog:" << count << endl;
    }
    void speak() override
    {
        cout << "wang" << endl;
    }
};

int Dog::count = 0;

class Cat : public Animal
{
protected:
    static int count;

public:
    Cat()
    {
        cout << "Cat" << endl;
        count++;
    }
    ~Cat()
    {
        count--;
    }
    static void getcount()
    {
        cout << "Cat:" << count << endl;
    }
    void speak() override
    {
        cout << "miao" << endl;
    }
};

int Cat::count = 0;

int main()
{
    int n, m, i = 0;
    cin >> n;
    cin >> m;
    Animal *a[20];

    for (; i < n; i++)
    {
        a[i] = new Dog;
    }
    Animal::getcount();
    Dog::getcount();

    for (; i < n + m; i++)
    {
        a[i] = new Cat;
    }
    Animal::getcount();
    Cat::getcount();

    for (int j = 0; j < n + m - 3; j++)
    { // 总量小于3时,不做删除
        a[j]->speak();
        delete a[j];
        a[j] = NULL;
    }
    Animal::getcount();
    Dog::getcount();
    Cat::getcount();
    return 0;
}

今天的内容就分享这么多
求三连!!!
求关注!!!

  • 20
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
代码中,不能直接将List<Object>强制转换为ArrayList<SUDto>。这是因为List<Object>和ArrayList<SUDto>是不同类型的集合,它们之间没有继承关系。如果你尝试这样的强制转换,会导致编译错误。 解决这个问题的方法是使用遍历来逐个将List<Object>中的元素转换为SUDto对象,然后将它们添加到一个新的ArrayList<SUDto>中。你可以使用Java 8中的流式操作和lambda表达式来实现这个转换过程。 以下是一个示例代码片段,演示了如何将List<Object>转换为ArrayList<SUDto>: List<Object> sourceList = new ArrayList<>(); // 原始的List<Object>对象 ArrayList<SUDto> targetList = new ArrayList<>(); // 目标的ArrayList<SUDto>对象 sourceList.stream() // 将List<Object>转换为流 .map(obj -> (SUDto) obj) // 将每个元素转换为SUDto对象 .forEach(targetList::add); // 将转换后的对象添加到目标ArrayList<SUDto>中 现在,targetList就是你想要的类型为ArrayList<SUDto>的集合了。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* [Java ListObject分组转成ListListObject 中报 java.util.HashMap$Values cannot be cast to ...](https://blog.csdn.net/qq_34828100/article/details/110430173)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] - *3* [JAVA多态 ListString转为ListObject方法](https://blog.csdn.net/qq_40301372/article/details/128294586)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 50%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

NineSense

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值