1. 设计思路
本实战的实质是完成对学生成绩信息的建立、查找、插入、修改、删除等功能,可以首先定义项目的数据结构,然后将每个功能写成一个函数来完成对数据的操作,最后完成主函数以验证各个函数功能并得出运行结果。
2. 数据结构
本项目的数据是一组学生的成绩信息,每条学生的成绩信息由学号、姓名和成绩组成,这组学生的成绩信息具有相同特性,属于同一数据对象,相邻数据元素之间存在序偶关系。由此可以看出,这些数据具有线性表中数据元素的性质,所以该系统的数据采用线性表来存储。
顺序表是线性表的顺序存储结构,是指用一组连续的内存单元依次存放线性表的数据元素。在顺序存储结构下,逻辑关系相邻的两个元素在物理位置上也相邻,这是顺序表的特点。本项目可以采用顺序表的线性表顺序存储结构。
若一个数据元素仅占一个存储单元,则其存储方式参见下图。
从图中可见,第 i
个数据元素的地址为
Loc(ai)=loc(a1)+(i-1)
假设线性表中每个元素占用 k
个存储单元,那么在顺序表中,线性表的第 i
个元素的存储位置与第 1 个元素的存储位置的关系是
Loc(ai)=loc(a1)+(i-1)*k
这里 Loc(ai)
是第 i
个元素的存储位置,loc(a1)
是第 1 个元素的存储位置,也称为线性表的基址。显然,顺序表便于进行随机访问,故线性表的顺序存储结构是一种随机存储结构。
顺序表适宜于做查找这样的静态操作;顺序存储的优点是存储密度大,存储空间利用率高。缺点是插入或删除元素时不方便。
用结构体类型定义每个学生数据,故该数组中的每个数据的结构可描述为:
typedef struct StudentTag
{
std::string id;
std::string name;
int age;
float score;
}Student;
3. 程序清单
project.h
文件:
#include <iostream>
#include <string>
typedef struct StudentTag
{
std::string id;
std::string name;
int age;
float score;
// 结构体初始化
StudentTag(std::string i="", std::string n="", int a=0, float s=0.0)
{
id = i;
name = n;
age = a;
score = s;
}
}Student;
class LinearList
{
public:
LinearList(int size);
~LinearList();
void init_list();
void clear_list();
bool is_empty();
bool is_full();
int print_list();
int get_list_length();
int get_element(int i, Student &data);
int insert_element(int i, Student data);
int delete_element(int i, Student &data);
int update_element(int i, Student data);
private:
Student *stu;
int length;
int cap;
};
project.cpp
#include "project.h"
LinearList::LinearList(int size)
{
stu = new Student[size];
if(stu == NULL)
{
std::cout << " new error" << std::endl;
}
length = 0;
cap = size;
std::cout << "constructor done" << std::endl;
}
LinearList::~LinearList()
{
if(stu != NULL)
{
delete[] stu;
stu = NULL;
length = 0;
cap = 0;
}
std::cout << "destructor done" << std::endl;
}
void LinearList::init_list()
{
std::cout << "init_list start" << std::endl;
stu->id = "00001";
stu->name = "Tom";
stu->age = 18;
stu->score = 99.5;
(stu+1)->id = "00002";
(stu+1)->name = "Jack";
(stu+1)->age = 19;
(stu+1)->score = 98;
length += 2;
std::cout << "init_list done" << std::endl;
}
void LinearList::clear_list()
{
std::cout << "clear_list start" << std::endl;
for(int i=0; i<length; ++i)
{
(stu+i)->id = "";
(stu+i)->name = "";
(stu+i)->age = 0;
(stu+i)->score = 0;
}
length = 0;
cap = 0;
std::cout << "clear_list done" << std::endl;
}
bool LinearList::is_empty()
{
return length == 0 ? true : false;
}
bool LinearList::is_full()
{
return length == cap && length != 0 ? true : false;
}
int LinearList::print_list()
{
for(int i=0; i<length; ++i)
{
std::cout << "id:" << (stu+i)->id << " "
<< "name:" << (stu+i)->name << " "
<< "age:" << (stu+i)->age << " "
<< "score:" << (stu+i)->score << " "
<< std::endl;
}
return 0;
}
int LinearList::get_list_length()
{
return length;
}
int LinearList::get_element(int i, Student &data)
{
if(i < 1 || i > length)
{
std::cout << "i is not in (1, " << length << ")" << std::endl;
return -1;
}
data = *(stu + i - 1);
return 0;
}
int LinearList::insert_element(int i, Student data)
{
if(i < 1 || i > cap)
{
std::cout << "i is not in (1, " << cap << ")" << std::endl;
return -1;
}
// 要插入的元素在原始线性表最后一个元素之后
if(i >= length)
{
*(stu + length) = data;
}
else // 要插入的元素在原始线性表第一个元素和最后一个元素之间
{
for(int j=length; j>=i; --j)
{
*(stu + j + 1) = *(stu + j);
}
*(stu + i) = data;
}
length += 1;
return 0;
}
int LinearList::delete_element(int i, Student &data)
{
if(is_empty() || (i < 1 || i > length))
{
return -1;
}
data = *(stu + i - 1);
for(int j=i; j<length; ++j)
{
*(stu + j - 1 ) = *(stu + j);
}
length -= 1;
return 0;
}
int LinearList::update_element(int i, Student data)
{
if(i < 1 || i >= length)
{
std::cout << "i is not in (1, " << length << ")" << std::endl;
return -1;
}
*(stu + i - 1) = data;
return 0;
}
main.cpp
#include "project.cpp"
int main()
{
LinearList L(10);
L.init_list();
L.print_list();
// L.clear_list();
// L.print_list();
bool is_empty = L.is_empty();
std::cout << "is_empty: " << is_empty << std::endl;
bool is_full = L.is_full();
std::cout << "is_full: " << is_full << std::endl;
std::cout << "length: " << L.get_list_length() << std::endl;
Student s;
L.get_element(2, s);
std::cout << "第 2 个元素为 " << "id:" << s.id << " "
<< "name:" << s.name << " "
<< "age:" << s.age << " "
<< "score:" << s.score << " "
<< std::endl;
Student si("00003", "wohu", 18, 97);
L.insert_element(2, si);
std::cout << "插入元素之后的结果" << std::endl;
L.print_list();
Student sd;
L.delete_element(1, sd);
std::cout << "要删除的元素为 " << "id:" << sd.id << " "
<< "name:" << sd.name << " "
<< "age:" << sd.age << " "
<< "score:" << sd.score << " "
<< std::endl;
std::cout << "删除元素之后的结果" << std::endl;
L.print_list();
Student su("00004", "kuku", 20, 94);
std::cout << "要更改的元素为 " << "id:" << su.id << " "
<< "name:" << su.name << " "
<< "age:" << su.age << " "
<< "score:" << su.score << " "
<< std::endl;
L.update_element(1, su);
std::cout << "更新元素之后的结果" << std::endl;
L.print_list();
}