CPP2023-030-模板 (whx)(真名我就不打了,害怕我也成谈资)

目录

前言 老规矩,强者直接转源代码

题目

6-1

类模板:

裁判测试程序样例:

输入样例:

输出样例:

6-2

函数接口定义:sort函数将接受size个数据,将它们从小到大排序后存在a指向的一段连续空间中。

裁判测试程序样例:

输入样例:

输出样例:

6-3

函数接口定义:

裁判测试程序样例:

输入样例:

输出样例:

6-4

裁判测试程序样例:

输入样例:

输出样例:

解析

6-1 有序数组(类模板)

6-2 数组排序输出(函数模板)

6-3 vector

6-4 你好,类模板(圆的面积)

源代码

6-1

6-2

6-3

6-4


前言 老规矩,强者直接转源代码

题目

6-1

实现一个类模板,它可以接受一组数据,能对数据排序,也能输出数组的内容。

每行输入的第一个数字为0,1,2或3:为0时表示输入结束; 为1时表示将输入整数,为2时表示将输入有一位小数的浮点数,为3时表示输入字符。

如果第一个数字非0,则接下来将输入一个正整数,表示即将输入的数据的数量。

从每行第三个输入开始,依次输入指定类型的数据。

类模板:

template <class T> class MyArray

裁判测试程序样例:

#include <iostream>
using namespace std;

/* 请在这里填写答案 */

template<class T>
MyArray<T>::~MyArray(){ delete[] data;}

template<class T>
bool MyArray<T>::check(){
    int i;
    for(i=0;i<size-1;i++)
        if(data[i]>data[i+1]) { cout<<"ERROR!"<<endl;return false;}
    return true;
}
int main( )
{
    MyArray<int> *pI;
    MyArray<float> *pF;
    MyArray<char> *pC;
    int ty, size;
    cin>>ty;
    while(ty>0){
        cin>>size;
        switch(ty){
            case 1: pI = new MyArray<int>(size);   pI->sort(); pI->check(); pI->display(); delete pI; break;
            case 2: pF = new MyArray<float>(size); pF->sort(); pF->check(); pF->display(); delete pF; break;
            case 3: pC = new MyArray<char>(size);  pC->sort(); pC->check(); pC->display(); delete pC; break;
        }
        cin>>ty;
    }
    return 0;
}

输入样例:

1 3 2 3 1
2 4 1.5 2.6 3.7 0.5
3 2 A a
0

输出样例:

1 2 3
0.5 1.5 2.6 3.7
A a

6-2

对于输入的每一批数,按从小到大排序后输出。

一行输入为一批数,第一个输入为数据类型(1表示整数,2表示字符型数,3表示有一位小数的浮点数,4表示字符串,0表示输入结束),第二个输入为该批数的数量size(0<size<=10),接下来为size个指定类型的数据。

输出将从小到大顺序输出数据。

函数接口定义:sort函数将接受size个数据,将它们从小到大排序后存在a指向的一段连续空间中。

template <class T> void sort(T *a, int size);

裁判测试程序样例:

#include <iostream>
#include <string>
using namespace std;

/* 请在这里填写答案 */

template <class T>
void display(T* a, int size){
    for(int i=0; i<size-1; i++) cout<<a[i]<<' ';
    cout<<a[size-1]<<endl;
}
int main() {
     const int SIZE=10;
     int a[SIZE];
     char b[SIZE];
     double c[SIZE];
     string d[SIZE];
     int ty, size;
     cin>>ty;
     while(ty>0){
         cin>>size;
         switch(ty){
             case 1:sort(a,size); display(a,size); break;
             case 2:sort(b,size); display(b,size); break;
             case 3:sort(c,size); display(c,size); break;
             case 4:sort(d,size); display(d,size); break;
         }
         cin>>ty;
     }
      return 0;
}

输入样例:

1 3 3 2 1
2 2 a A
3 3 1.5 2.6 2.2
4 2 bca abc
0

输出样例:

1 2 3
A a
1.5 2.2 2.6
abc bca

6-3

本题要求实现一个Vector类模板,能实现数据的存储和访问。通过[]运算符访问时只能访问已经存在的元素,而通过add()方法访问时可以自动扩展内部存储空间。

注意,这个Vector的行为和std::vector是不同的

函数接口定义:

template <class T> class Vector { ...

裁判测试程序样例:

#include <iostream>
using namespace std;

/* 请在这里填写答案 */

int main()
{
    Vector<int> vint;
    int n,m;
    cin >> n >> m;
    for ( int i=0; i<n; i++ ) {
        //    add() can inflate the vector automatically
        vint.add(i);    
    }
    //    get_size() returns the number of elements stored in the vector
    cout << vint.get_size() << endl;
    cout << vint[m] << endl;
    //    remove() removes the element at the index which begins from zero
    vint.remove(m);
    cout << vint.add(-1) << endl;
    cout << vint[m] << endl;
    Vector<int> vv = vint;
    cout << vv[vv.get_size()-1] << endl;
    vv.add(m);
    cout << vint.get_size() << endl;
}

输入样例:

100 50

输出样例:

100
50
99
51
-1
100

6-4

完善Square的定义,使得程序正确运行:

裁判测试程序样例:

#include <iostream>
using namespace std;

// 请将答案填写在这里

int main() {
    int width1;
    cin >> width1; // 输入正方形的边长
    Square<int> square1(width1);
    cout << square1.getArea() << endl; // 输出正方形的面积

    double width2;
    cin >> width2; // 输入正方形的边长
    Square<double> square2(width2);
    cout << square2.getArea() << endl; // 输出正方形的面积

    return 0;
}

输入样例:

在这里给出一组输入。例如:

3
1.1

输出样例:

在这里给出相应的输出。例如:

9
1.21

解析

这边头文件我就不写了,可以先都用<iostream>看看报错缺啥

要是实在有人找不出来用什么(不会吧不会吧),那就<bits/stdc++.h>

6-1 有序数组(类模板)

template <class T>
class MyArray
{
public:
 
    bool check();
    ~MyArray();
    MyArray(int);
    void sort();
    void display();
private:
     int size;
     T* data;
};

bool check(); 一个用来检查数组的方法

~MyArray(); 析构函数,用来释放对象占用的内存

MyArray(int); 构造函数,用来初始化数组,需要传入数组的大小作为参数

void sort(); 一个用来对数组进行排序的方法

void display(); 一个用来显示数组内容的方法

T* data; 一个指向模板类型 T 的指针,用来存储数组的数据

类里面的函数就叫做方法

我个人的习惯是看完题之后,把要用的函数都声明一下(最后在去掉嘛),不过先写功能再声明也无所谓了,仁者见仁智者见智吧

template<class T>
MyArray<T>::MyArray(int s)
{
 size=s;
 data=new T[size];
 for(int i=0;i<size;i++)
 cin>>data[i];
}

这段代码是类模板 MyArray 的构造函数 MyArray(int s) 的实现部分。在这里,template<class T> 表示这是类模板 MyArray 的成员函数。

在构造函数中,传入一个整数参数 s,表示数组的大小。然后,将类中的 size 成员变量设置为传入的大小 s。接着,使用 new (申请的堆上的空间,咱们一般直接申请的都是栈上的)(栈由操作系统自动分配释放,无需我们手动控制;堆的申请和释放工作由程序员控制,容易产生内存泄漏;)运算符动态分配了一个大小为 size 的类型为 T 的数组,并将指针赋值给类中的 data 成员变量。

然后,使用一个循环遍历数组,通过 cin 从标准输入中依次输入数组中的元素。每次循环,将输入的元素存储到数组的对应位置 data[i] 中。

总之,这段代码实现了类模板 MyArray 的构造函数,用于动态分配存储空间并从标准输入中读取数据存储到数组中。

(堆和栈具体区别建议看这个去具体了解一下https://blog.csdn.net/K346K346/article/details/80849966/?ops_request_misc=&request_id=&biz_id=102&utm_term=%E5%A0%86%E5%92%8C%E6%A0%88%E7%9A%84%E5%8C%BA%E5%88%AB%E5%92%8C%E8%81%94%E7%B3%BB&utm_medium=distribute.pc_search_result.none-task-blog-2~all~sobaiduweb~default-1-80849966.142^v96^pc_search_result_base4&spm=1018.2226.3001.4449

template<class T>
 void MyArray<T>::display()
{
    for(int i=0; i<size-1; i++) cout<<data[i]<<' ';
    cout<<data[size-1]<<endl;
}

 

这段代码是类模板 MyArray 的成员函数 display() 的实现部分。template<class T> 表示的跟上面那个意思一样哈。

使用一个循环遍历数组,从下标 0 到 size-1,输出数组中的元素到标准输出流 cout 中,每个元素之间用空格分隔。(注意上下两段中这两个size-1的含义是不一样的)

循环结束后,再输出数组中最后一个元素 data[size-1] 到标准输出流 cout 中,然后换行。

总之,这段代码实现了类模板 MyArray 的成员函数 display(),用于在标准输出中显示数组中的元素。

template<class T>
 void MyArray<T>::sort()
{
    for(int i=0; i<size; i++)
    {
        int min=i;
        for(int j=i+1; j<size; j++)
        {
            if(data[min]>data[j])
            {
                min=j;
            }
        }
        if(min!=i)
        {
            T temp=data[min];
            data[min]=data[i];
            data[i]=temp;
        }
    }
}
 

这是一个插入排序哈,换成冒泡和选择也是whatever的,注意temp的类型是T就行了

6-2 数组排序输出(函数模板)

template <class T>
void sort(T *arr, int size)
{
    for(int i=0;i<size;i++)
    {
        cin>>arr[i];
    }
    /*
    for(int i=0; i<size; i++)
    {
        int min=i;
        for(int j=i+1; j<size; j++)
        {
            if(a[min]>a[j])
            {
                min=j;
            }
        }
        if(min!=i)
        {
            T temp=a[min];
            a[min]=a[i];
            a[i]=temp;
        }
    }
    */
	int j,i; 
	T tem;
	for (i = 0; i < size-1;i ++)//size-1是因为不用与自己比较,所以比的数就少一个
	{
		int count = 0;
		for (j = 0; j < size-1 - i; j++)	//size-1-i是因为每一趟就会少一个数比较
		{
			if (arr[j] > arr[j+1])//这是升序排法,前一个数和后一个数比较,如果前数大则与后一个数换位置
			{
				tem = arr[j];
				arr[j] = arr[j+1];
				arr[j+1] = tem;
				count = 1;
				
			}
		}
		if (count == 0)			//如果某一趟没有交换位置,则说明已经排好序,直接退出循环
				break;	
	}


}
 

这边注释里面的排序方法也是可以直接用的,建议是各种排序方法都自己写一遍,这个还没6-1难,6-1理解了,这个简单的跟喝水一样,所以我就不多赘述喽。

6-3 vector

template <class T>
class Vector
{
        int tos=0;     //创建一个整数用于下标表示
        const int size=100; //创建一个常数用于表示动态申请空间大小
        T*data;  //定义一个指针,用于动态申请空间
public:
    Vector()    //构造函数动态申请空间
    {
        data=new T[size];  
    }

 data=new T[size]; 就是在堆上开辟一个名为data的动态数组

    int  add(int  i)
    {
        //data=new T[size];  //不能在add函数里申请空间,因为作用域小了,add函数结束空间就被自己注销了
        data[tos]=i; //存入数组
        tos++;
        return  tos-1; //返回tos-1是根据main函数结果来的
    }

 这个函数用于向数组中添加一个新的元素 i

在函数内部,首先将元素 i 存储到数组的 tos 位置(tos 是一个表示下一个可用位置的索引),然后递增 tos,最后返回 tos-1,表示添加的元素的索引。

    int   get_size()
    {
        return tos;  //下标就代表了数组大小
    }

 这个函数用于返回数组的大小,即 tos 的值。

因为 tos 表示下一个可用位置的索引,所以它也代表了数组的大小。

    void remove(int m)
    {
        for(int i=m; i<tos-1; i++) //移除某个值后后面的值需要填补上,
        {
            data[i]=data[i+1];
        }
        tos--;
    }

 这个函数用于移除数组中的某个元素。

在函数内部,通过循环将索引大于等于 m 的元素向前移动一位,然后递减 tos

    const  T&  operator[](int i)//重载了[]运算符
    {
        return data[i];
    }
 
};

 这个函数是重载了 [] 运算符,用于通过索引访问数组中的元素。

它返回一个对数组元素的引用,允许用户读取数组中的元素,但不允许修改它们。

6-4 你好,类模板(圆的面积)

template <class T>
class Square {
private:
    T width; // 正方形的边长

public:
    Square(T w) { width = w; } // 构造函数
    T getArea() { return width * width; } // 计算正方形的面积
};

没啥东西,经过上面的练习,相信兄弟们已经知道这个有多简单了。

源代码

6-1

#include <iostream>
using namespace std;

/* 请在这里填写答案 */
template <class T>
class MyArray
{
public:
 
    bool check();
    ~MyArray();
    MyArray(int);
    void sort();
    void display();
private:
     int size;
     T* data;
};
 
 
template<class T>
MyArray<T>::MyArray(int s)
{
 size=s;
 data=new T[size];
 for(int i=0;i<size;i++)
 cin>>data[i];
}
 
 
template<class T>
 void MyArray<T>::display()
{
    for(int i=0; i<size-1; i++) cout<<data[i]<<' ';
    cout<<data[size-1]<<endl;
}
 
 
 
template<class T>
 void MyArray<T>::sort()
{
    for(int i=0; i<size; i++)
    {
        int min=i;
        for(int j=i+1; j<size; j++)
        {
            if(data[min]>data[j])
            {
                min=j;
            }
        }
        if(min!=i)
        {
            T temp=data[min];
            data[min]=data[i];
            data[i]=temp;
        }
    }
}
 

template<class T>
MyArray<T>::~MyArray(){ delete[] data;}

template<class T>
bool MyArray<T>::check(){
    int i;
    for(i=0;i<size-1;i++)
        if(data[i]>data[i+1]) { cout<<"ERROR!"<<endl;return false;}
    return true;
}
int main( )
{
    MyArray<int> *pI;
    MyArray<float> *pF;
    MyArray<char> *pC;
    int ty, size;
    cin>>ty;
    while(ty>0){
        cin>>size;
        switch(ty){
            case 1: pI = new MyArray<int>(size);   pI->sort(); pI->check(); pI->display(); delete pI; break;
            case 2: pF = new MyArray<float>(size); pF->sort(); pF->check(); pF->display(); delete pF; break;
            case 3: pC = new MyArray<char>(size);  pC->sort(); pC->check(); pC->display(); delete pC; break;
        }
        cin>>ty;
    }
    return 0;
}

6-2

#include <iostream>
#include <string>
using namespace std;

/* 请在这里填写答案 */
template <class T>
void sort(T *arr, int size)
{
    for(int i=0;i<size;i++)
    {
        cin>>arr[i];
    }
    /*
    for(int i=0; i<size; i++)
    {
        int min=i;
        for(int j=i+1; j<size; j++)
        {
            if(a[min]>a[j])
            {
                min=j;
            }
        }
        if(min!=i)
        {
            T temp=a[min];
            a[min]=a[i];
            a[i]=temp;
        }
    }
    */
	int j,i; 
	T tem;
	for (i = 0; i < size-1;i ++)//size-1是因为不用与自己比较,所以比的数就少一个
	{
		int count = 0;
		for (j = 0; j < size-1 - i; j++)	//size-1-i是因为每一趟就会少一个数比较
		{
			if (arr[j] > arr[j+1])//这是升序排法,前一个数和后一个数比较,如果前数大则与后一个数换位置
			{
				tem = arr[j];
				arr[j] = arr[j+1];
				arr[j+1] = tem;
				count = 1;
				
			}
		}
		if (count == 0)			//如果某一趟没有交换位置,则说明已经排好序,直接退出循环
				break;	
	}


}
 


template <class T>
void display(T* a, int size){
    for(int i=0; i<size-1; i++) cout<<a[i]<<' ';
    cout<<a[size-1]<<endl;
}
int main() {
     const int SIZE=10;
     int a[SIZE];
     char b[SIZE];
     double c[SIZE];
     string d[SIZE];
     int ty, size;
     cin>>ty;
     while(ty>0){
         cin>>size;
         switch(ty){
             case 1:sort(a,size); display(a,size); break;
             case 2:sort(b,size); display(b,size); break;
             case 3:sort(c,size); display(c,size); break;
             case 4:sort(d,size); display(d,size); break;
         }
         cin>>ty;
     }
      return 0;
}

6-3

#include<bits/stdc++.h>
using namespace std;


template <class T>
class Vector
{
        int tos=0;     //创建一个整数用于下标表示
        const int size=100; //创建一个常数用于表示动态申请空间大小
        T*data;  //定义一个指针,用于动态申请空间
public:
    Vector()    //构造函数动态申请空间
    {
        data=new T[size];  
    }
    int  add(int  i)
    {
        //data=new T[size];  //不能在add函数里申请空间,因为作用域小了,add函数结束空间就被自动注销了
        data[tos]=i; //存入数组
        tos++;
        return  tos-1; //返回tos-1是根据main函数结果来的
    }
  int   get_size()
  {
      return tos;  //下标就代表了数组大小
  }
void   remove(int   m)
{
    for(int i=m; i<tos-1; i++) //移除某个值后后面的值需要填补上,
    {
        data[i]=data[i+1];
    }
    tos--;
}
 
const  T&  operator[](int i)//重载了[]运算符
{
    return data[i];
}
 
};
int main() {
    Vector<int> vint;
    int n, m;
    cin >> n >> m;
    for (int i = 0; i < n; i++) {
        vint.add(i);
    }
    cout << vint.get_size() << endl;
    cout << vint[m] << endl;
    vint.remove(m);
    cout << vint.add(-1) << endl;
    cout << vint[m] << endl;
    Vector<int> vv = vint;
    cout << vv[vv.get_size() - 1] << endl;
    vv.add(m);
    cout << vint.get_size() << endl;

    return 0;
}

6-4

#include <iostream>
using namespace std;

template <class T>
class Square {
private:
    T width; // 正方形的边长

public:
    Square(T w) { width = w; } // 构造函数
    T getArea() { return width * width; } // 计算正方形的面积
};

int main() {
    int width1;
    cin >> width1; // 输入正方形的边长
    Square<int> square1(width1);
    cout << square1.getArea() << endl; // 输出正方形的面积

    double width2;
    cin >> width2; // 输入正方形的边长
    Square<double> square2(width2);
    cout << square2.getArea() << endl; // 输出正方形的面积

    return 0;
}

  • 24
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值