在线性结构中,各数据项按照一个线性次序构成一个整体。最基本的线性结构统称为序列(sequence),根据其中数据项的逻辑次序与其物理存储地址的对应关系不同,又可进一步地将序列区分为向量(vector)和链表(linked list)。在向量中,所有数据项的物理存放位置与其逻辑次序完全吻合,此时的逻辑次序也称作秩(rank);而在链表中,逻辑上相邻的数据项在物理上未必相邻,而是采用间接寻址的方式通过封装后的位置(position)相互引用。
数组是一种将标量数据聚集成更大数据类型的方式。对于数据类型T和整形常数N,声明如下:
T A[N];
起始位置表示为xA。这个声明有两个效果。首先,他在内存中分配了一个LN字节的连续区域,这里L是数据类型T的大小。齐次,它引入了标识符A,可以用A来作为指向数组开头的指针,这个指针的值就是xA。可以用0~N-1的整数索引来访问该数组元素。数组元素i会被存放在地址为xA+Li的地方。
按照面向对象思想中的数据抽象原则,可以对以上数组结构做一般性推广。向量就是数组的一种抽象与泛化,它也是由具有线性次序的一组元素构成的集合,其中的元素由秩相互区分。
Vector模板类
//
// Created by Junjie Liao on 2018-11-01.
//
#ifndef DATA_STRUCTURES_VECTOR_H
#define DATA_STRUCTURES_VECTOR_H
#include <iostream>
#include "../Sorting/Quicksort.h"
#include "../Sorting/RandomShuffle.h"
#include "../Searching/BinarySearch.h"
using namespace std;
#define DEFAULT_CAPACITY 1
template<typename T>
class Vector;
using Rank = int;
template<typename T>
class Vector {
public:
// Constructors
explicit Vector(int size = 0, int capacity = DEFAULT_CAPACITY, T element = (T) 0);
Vector(const T *A, Rank first, Rank last); // [first, last]
Vector(const T *A, int size);
Vector(const Vector<T> &V, Rank first, Rank last); // [first, last]
Vector(const Vector<T> &V);
// Destructor
~Vector();
// Static interfaces
int size() const;
bool empty() const;
bool disordered(Rank first, Rank last) const; // [first, last]
bool disordered() const;
bool sorted(Rank first, Rank last) const; // [first, last]
bool sorted() const;
Rank find(Rank first, Rank last, const T &key) const; // [first, last]
Rank find(const T &key) const;
Rank search(Rank first, Rank last, const T &key) const; // [first, last]
Rank search(const T &key) const;
// Dynamic interfaces
Rank insert(Rank rank, const T &element);
Rank insert_sorted(const T &element);
Rank push_front(const T &element);
Rank push_back(const T &element);
int erase(Rank first, Rank last); // [first, last]
int clear();
T erase(Rank rank);
T pop_front();
T pop_back();
void shuffle(Rank first, Rank last); // [first, last]
void shuffle();
void sort(Rank first, Rank last); // [first, last]
void sort();
void reverse();
int unique_disordered();
int unique_sorted();
// Operator overloading
T &operator[](Rank rank) const;
Vector<T> &operator=(const Vector<T> &V);
// Traversal
void traverse(void (*visit)(T &element));
template <typename VISIT>
void traverse(VISIT &visit);
protected:
int __size{};
int __capacity{};
T *__A{};
void copy(const T *A, Rank first, Rank last); // [first, last]
void expand();
void contract();
};
#endif
template<typename T>
void Vector<T>::copy(const T *A, Rank first, Rank last) {
__A = new T[__capacity = (last - first) << 1];
for (__size = 0; first < last; __A[__size++] = A[first++]);
}
template<typename T>
Vector<T>::Vector(int size, int capacity, T element) {
__A = new T[__capacity = capacity];
for (__size = 0; __size < size; __A[__size++] = element);
}
template<typename T>
Vector<T>::Vector(const T *A, Rank first, Rank last) {
__A = new T[__capacity = (last - first) << 1];
for (__size = 0; first < last; __A[__size++] = A[first++]);
}
template<typename T>
Vector<T>::Vector(const T *A, int size): Vector{A, 0 , size} {}
template<typename T>
Vector<T>::Vector(const Vector<T> &V, Rank first, Rank last): Vector{V.__A, first, last} {}
template<typename T>
Vector<T>::Vector(const Vector<T> &V): Vector{V.__A, 0, V.__size} {}
template<typename T>
Vector<T>::~Vector() {
delete __A;
}
template<typename T>
int Vector<T>::size() const {
return __size;
}
template<typename T>
bool Vector<T>::empty() const {
return !__size;
}
template<typename T>
bool Vector<T>::disordered(Rank first, Rank last) const {
for (Rank rank = first + 1; rank < last; rank++) {
if (__A[rank - 1] > __A[rank]) return true;
}
return false;
}
template<typename T>
bool Vector<T>::disordered() const {
return disordered(0, __size);
}
template<typename T>
bool Vector<T>::sorted(Rank first, Rank last) const {
return !disordered(first, last);
}
template<typename T>
bool Vector<T>::sorted() const {
return sorted(0, __size);
}
template<typename T>
Rank Vector<T>::find(Rank first, Rank last, const T &key) const {
while (first < last-- && key != __A[last]);
return last;
}
template<typename T>
Rank Vector<T>::find(const T &key) const {
return find(0, __size, key);
}
template<typename T>
Rank Vector<T>::search(Rank first, Rank last, const T &key) const {
return binary_search(__A, first, last, key);
}
template<typename T>
Rank Vector<T>::search(const T &key) const {
return search(0, __size, key);
}
template<typename T>
Rank Vector<T>::insert(Rank rank, const T &element) {
if (__size == __capacity) expand();
for (Rank reserve = __size; reserve > rank; __A[reserve--] = __A[reserve - 1]);
__A[rank] = element;
__size++;
return rank;
}
template<typename T>
Rank Vector<T>::insert_sorted(const T &element) {
return insert(search(element) + 1, element);
}
template<typename T>
Rank Vector<T>::push_front(const T &element) {
return insert(0, element);
}
template<typename T>
Rank Vector<T>::push_back(const T &element) {
return insert(__size, element);
}
template<typename T>
int Vector<T>::erase(Rank first, Rank last) {
while (last < __size) __A[first++] = __A[last++];
__size = first;
if (__size << 2 < __capacity) contract();
return last - first;
}
template<typename T>
T Vector<T>::erase(Rank rank) {
T element = __A[rank];
erase(rank, rank + 1);
return element;
}
template<typename T>
int Vector<T>::clear() {
return erase(0, __size);
}
template<typename T>
T Vector<T>::pop_front() {
return erase(0);
}
template<typename T>
T Vector<T>::pop_back() {
return erase(__size - 1);
}
template<typename T>
void Vector<T>::shuffle(Rank first, Rank last) {
random_shuffle(__A, first, last);
}
template<typename T>
void Vector<T>::shuffle() {
shuffle(0, __size);
}
template<typename T>
void Vector<T>::sort(Rank first, Rank last) {
quicksort(__A, first, last);
}
template<typename T>
void Vector<T>::sort() {
sort(0, __size);
}
template<typename T>
void Vector<T>::reverse() {
Rank low = 0;
Rank high = __size - 1;
while (low < high) swap(__A[low++], __A[high--]);
}
template<typename T>
int Vector<T>::unique_disordered() {
int old_size = __size;
for (Rank rank = 1; rank < __size; find(0, rank, __A[rank]) < 0 ? rank++ : erase(rank));
return old_size - __size;
}
template<typename T>
int Vector<T>::unique_sorted() {
int unique = 0;
Rank rank = 0;
while (++rank < __size) {
if (__A[unique] != __A[rank]) __A[++unique] = __A[rank];
}
__size = ++unique;
if (__size << 1 < __capacity) contract();
return rank - unique;
}
template<typename T>
T &Vector<T>::operator[](Rank rank) const {
return __A[rank];
}
template<typename T>
Vector<T> &Vector<T>::operator=(const Vector<T> &V) {
if (__A) delete [] __A;
copy(V.__A, 0, V.__size);
return *this;
}
template<typename T>
void Vector<T>::traverse(void (*visit)(T &element)) {
for (Rank rank = 0; rank < __size; visit(__A[rank++]));
}
template<typename T>
template<typename VISIT>
void Vector<T>::traverse(VISIT &visit) {
for (Rank rank = 0; rank < __size; visit(__A[rank++]));
}
template<typename T>
void Vector<T>::expand() {
auto *new_elements = new T[__capacity <<= 1];
for (Rank rank = 0; rank < __size; new_elements[rank++] = __A[rank]);
delete [] __A;
__A = new_elements;
}
template<typename T>
void Vector<T>::contract() {
__capacity = __size ? min(__size << 1, __capacity >> 1) : DEFAULT_CAPACITY;
auto *new_elements = new T[__capacity];
for (Rank rank = 0; rank < __size; new_elements[rank++] = __A[rank]);
delete [] __A;
__A = new_elements;
}