基于前面實現(xiàn)的數(shù)據(jù)結(jié)構(gòu)類模板基礎(chǔ),繼續(xù)完成基于順序存儲結(jié)構(gòu)的線性表的實現(xiàn),繼承關(guān)系圖如下:
涵江網(wǎng)站制作公司哪家好,找成都創(chuàng)新互聯(lián)!從網(wǎng)頁設(shè)計、網(wǎng)站建設(shè)、微信開發(fā)、APP開發(fā)、響應(yīng)式網(wǎng)站設(shè)計等網(wǎng)站項目制作,到程序開發(fā),運營維護。成都創(chuàng)新互聯(lián)2013年開創(chuàng)至今到現(xiàn)在10年的時間,我們擁有了豐富的建站經(jīng)驗和運維經(jīng)驗,來保證我們的工作的順利進行。專注于網(wǎng)站建設(shè)就選成都創(chuàng)新互聯(lián)。
線性表是具有相同類型的n(>=)個數(shù)據(jù)元素的有限序列,(a0, a1, a2... an-1),其中ai是表項,n是表長度。
性質(zhì):
template <typename T>
class List:public Object
{
protected:
List(const List&);
List& operator ==(const List&);
public:
List(){}
virtual bool insert(const T& e) = 0;
virtual bool insert(int i,const T& e) = 0;
virtual bool remove(int i) = 0;
virtual bool set(int i,const T& e) = 0;
virtual bool get(int i,T& e) const = 0;
virtual int length() const = 0;
virtual void clear() = 0;
};
線性表是數(shù)據(jù)元素的有序并且有限的集合,其中的數(shù)據(jù)元素類型相同,在程序中表現(xiàn)為一個特殊的數(shù)據(jù)結(jié)構(gòu),可以使用C++中的抽象類來表示,用來描述排隊關(guān)系的問題。
定義:
線性表的順序存儲結(jié)構(gòu),指的是用一段地址連續(xù)的存儲單元依次存儲線性表中的數(shù)據(jù)元素。
設(shè)計思路:
使用一維數(shù)組來實現(xiàn)存儲結(jié)構(gòu):
// 存儲空間:T* m_array; 當前長度:int m_length;
template <typename T>
class SeqList : public List<T>
{
protected:
T* m_array;
int m_length;
};
template <typename T>
class SeqList : public List<T>
{
protected:
T* m_array; // 順序存儲空間
int m_length; // 當前線性長度
public:
bool insert(int index, const T& e)
{
bool ret = ( (index>=0) && (index<=m_length) ); // <= 因為可以插入的點,必然比當前元素多1
if(ret && ( m_length < capacity() )) // 當前至少有一個空間可插入
{
for(int p=m_length-1; p>=index; p--)
{
m_array[p + 1] = m_array[p];
}
m_array[index] = e;
m_length++;
}
return ret;
}
bool insert(const T& e)
{
return insert(m_length, e);
}
bool remove(int index)
{
bool ret = ( (index>=0) && (index<m_length) ); // 目標位置合法 <m_length
if(ret)
{
for(int p=index; p<m_length-1; p++) // 注意思考此處的邊界條件
{
m_array[p] = m_array[p+1];
}
m_length--;
}
return ret;
}
bool set(int index, const T& e)
{
bool ret = ( (index>=0) && (index<m_length) );
if(ret)
{
m_array[index] = e;
}
return ret;
}
bool get(int index, T& e) const
{
bool ret = ( (index>=0) && (index<m_length) );
if(ret)
{
e = m_array[index];
}
return ret;
}
int length() const
{
return m_length;
}
void clear()
{
m_length = 0;
}
// 順序存儲表的數(shù)組訪問方式
T& operator [] (int index)
{
if( (index>=0) && (index<m_length) )
{
return m_array[index];
}
else
{
THROW_EXCEPTION(IndexOutOfBoundsException, "index out of range...");
}
}
T operator [] (int index) const
{
static_cast<SeqList<T>&>(*this)[index]; // 去除const屬性,然后調(diào)用非const版本實現(xiàn)
}
// 順序存儲表的的容量
virtual int capacity() const = 0;
};
類模板
template < typename T, int N >
class StaticList : public SeqList <T>
{
protected:
T m_space[]; // 順序存儲空間,N為模板參數(shù)
public:
StaticList(); // 指定父類成員的具體值
int capacity() const;
};
template < typename T, int N >
class StaticList : public SeqList <T>
{
protected:
T m_space[N]; // 順序存儲空間,N為模板參數(shù)
public:
StaticList() // 指定父類成員的具體值
{
this->m_array = m_space;
this->m_length = 0;
}
int capacity() const
{
return N;
}
};
類模板
template < typename T>
class DynamicList : public SeqList <T>
{
protected:
int capacity; // 順序存儲空間的大小
public:
DynamicList(int capacity); // 申請空間
int capacity(void) const // 返回capacity的值
// 重置存儲空間的大小
void reset(int capacity);
~DynamicList(); // 歸還空間
};
template <typename T>
class DynamicList : public SeqList<T>
{
protected:
int m_capacity;
public:
DynamicList(int capacity)
{
this->m_array = new T[capacity];
if(this->m_array != NULL)
{
this->m_length = 0;
this->m_capacity = capacity;
}
else
{
THROW_EXCEPTION(NoEnoughMemoryException,"No memory to create DynamicList object ...");
}
}
int capacity()const
{
return m_capacity;
}
void resize(int capacity)
{
if(capacity != m_capacity)
{
T* array = new T[capacity];
if(array != NULL)
{
int length = (this->m_length < capacity ? this->m_length : capacity);
for(int i=0;i<length;i++)
{
array[i] = this->m_array[i];
}
T* temp = this->m_array;
this->m_array = array;
this->m_length = length;
this->m_capacity = capacity;
delete[] temp;
}
else
{
THROW_EXCEPTION(NoEnoughMemoryException,"No memory to create DynamicList object ...");
}
}
}
~DynamicList()
{
delete[] this->m_array;
}
};
順序存儲結(jié)構(gòu)線性表的效率為O(n),主要受其插入和刪除操作的影響(譬如插入操作時,要插入位置之后的數(shù)據(jù)要向后挪動) 。
兩個長度相同的順序存儲結(jié)構(gòu)線性表,插入、刪除操作的耗時是否相同?
拷貝構(gòu)造和賦值操作會導(dǎo)致兩個指針指向同一個地址,導(dǎo)致內(nèi)存重復(fù)釋放。對于容器類型的類,可以考慮禁用拷貝構(gòu)造和賦值操作。
原因: 1、對于生活中容器類的東西,我們無法對其進行賦值(譬如生活中我們不可能將杯子中的水進行復(fù)制,只能使用另一個杯子重新去獲取等量的水)。
實現(xiàn):將拷貝構(gòu)造和賦值操作函數(shù)定義為proteced成員,在類的外部,不能使用。
protected:
List(const List&){}
List& operator = (const List&){}
線性表不能直接當做數(shù)組來使用
順序存儲結(jié)構(gòu)線性表提供了數(shù)組操作符的重載,可以直接像數(shù)組一樣,同過下標直接獲取目標位置的元素,在具體的使用上類似數(shù)組,但是本質(zhì)上不同,不能代替數(shù)組使用:
網(wǎng)頁名稱:數(shù)據(jù)結(jié)構(gòu)(03)_順序存儲結(jié)構(gòu)線性表
文章源于:http://www.2m8n56k.cn/article48/jcgchp.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供外貿(mào)網(wǎng)站建設(shè)、標簽優(yōu)化、面包屑導(dǎo)航、App開發(fā)、做網(wǎng)站、電子商務(wù)
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:[email protected]。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)