欧美一区二区三区老妇人-欧美做爰猛烈大尺度电-99久久夜色精品国产亚洲a-亚洲福利视频一区二区

數(shù)據(jù)結(jié)構(gòu)(三)——基于順序存儲(chǔ)結(jié)構(gòu)的線(xiàn)性表

數(shù)據(jù)結(jié)構(gòu)(三)——基于順序存儲(chǔ)結(jié)構(gòu)的線(xiàn)性表

一、基于順序存儲(chǔ)結(jié)構(gòu)的線(xiàn)性表實(shí)現(xiàn)

1、順序存儲(chǔ)的定義

    線(xiàn)性表的順序存儲(chǔ)結(jié)構(gòu)是用一段地址連續(xù)的存儲(chǔ)單元依次存儲(chǔ)線(xiàn)性表中的數(shù)據(jù)元素。

數(shù)據(jù)結(jié)構(gòu)(三)——基于順序存儲(chǔ)結(jié)構(gòu)的線(xiàn)性表

十年的藍(lán)田網(wǎng)站建設(shè)經(jīng)驗(yàn),針對(duì)設(shè)計(jì)、前端、開(kāi)發(fā)、售后、文案、推廣等六對(duì)一服務(wù),響應(yīng)快,48小時(shí)及時(shí)工作處理。全網(wǎng)整合營(yíng)銷(xiāo)推廣的優(yōu)勢(shì)是能夠根據(jù)用戶(hù)設(shè)備顯示端的尺寸不同,自動(dòng)調(diào)整藍(lán)田建站的顯示方式,使網(wǎng)站能夠適用不同顯示終端,在瀏覽器中調(diào)整網(wǎng)站的寬度,無(wú)論在任何一種瀏覽器上瀏覽網(wǎng)站,都能展現(xiàn)優(yōu)雅布局與設(shè)計(jì),從而大程度地提升瀏覽體驗(yàn)。創(chuàng)新互聯(lián)從事“藍(lán)田網(wǎng)站設(shè)計(jì)”,“藍(lán)田網(wǎng)站推廣”以來(lái),每個(gè)客戶(hù)項(xiàng)目都認(rèn)真落實(shí)執(zhí)行。

2、順序存儲(chǔ)結(jié)構(gòu)的操作

    使用一維數(shù)組實(shí)現(xiàn)順序存儲(chǔ)結(jié)構(gòu)。
template <typename T>
class SeqList:public List<T>
{
protected:
  T* m_array;//順序存儲(chǔ)空間
  int m_length;//當(dāng)前線(xiàn)性表的長(zhǎng)度
};
    一維順序存儲(chǔ)結(jié)構(gòu)可以是原生數(shù)組或是動(dòng)態(tài)分配的空間。因此,根據(jù)空間分配的不同,分為靜態(tài)線(xiàn)性表和動(dòng)態(tài)線(xiàn)性表。

(1)元素的獲取
順序存儲(chǔ)結(jié)構(gòu)的元素獲取操作:
A、判斷目標(biāo)位置是否合法
B、將目標(biāo)位置作為數(shù)組下標(biāo)獲取元素

bool get(int index, T& value)
{
  //判斷目標(biāo)位置是否合法
  bool ret = (0 <= index) && (index < m_length);
  if(ret)
  {
      //將目標(biāo)位置作為下標(biāo)獲取元素
      value = m_array[index];
  }
  return ret;
}

(2)元素的插入操作
順序存儲(chǔ)結(jié)構(gòu)的元素插入操作:
A、判斷目標(biāo)位置是否合法
B、將目標(biāo)位置后的所有元素向后移一位
C、將新元素插入目標(biāo)位置
D、線(xiàn)性表長(zhǎng)度增加1

bool insert(int index, const T& value)
{
  //判斷目標(biāo)位置是否合法
  bool ret = (0 <= index) && (index <= m_length);
  ret = ret && ((m_length + 1) <= capacity());
  if(ret)
  {
      //將目標(biāo)位置后的所有元素后移一個(gè)位置
      for(int i = m_length -1; index <= i; i--)
      {
          m_array[i+1] = m_array[i];
      }
      //將新元素插入到目標(biāo)位置
      m_array[index] = value;
      //線(xiàn)性表長(zhǎng)度加1
      m_length++;
  }
  return ret;
}

(3)元素的刪除操作
順序存儲(chǔ)結(jié)構(gòu)的元素刪除操作:
A、判斷目標(biāo)位置是否合法
B、將目標(biāo)位置后的所有元素前移一個(gè)位置
C、線(xiàn)性表長(zhǎng)度減1

bool remove(int index)
{
  //判斷目標(biāo)位置是否合法
  bool ret = (0 <= index) && (index < m_length);
  if(ret)
  {
      //將目標(biāo)位置后的所有元素前移一位
      for(int i = index; i < m_length-1; i++)
      {
          m_array[i] = m_array[i+1];
      }
      //將線(xiàn)性表長(zhǎng)度減1
      m_length--;
  }
  return ret;
}

(4)元素值的修改
順序存儲(chǔ)結(jié)構(gòu)中元素值的修改:
A、判斷目標(biāo)位置是否合法
B、修改目標(biāo)位置元素的值

bool set(int index, const T& value)
{
  //判斷目標(biāo)位置是否合法
  bool ret = (0 <= index) && (index < m_length);
  if(ret)
  {
      //修改目標(biāo)位置元素的值
      m_array[index] = value;
  }
  return ret;
}

(5)線(xiàn)性表長(zhǎng)度的獲取
順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表的長(zhǎng)度獲取

int length()const
{
  //線(xiàn)性表長(zhǎng)度
  return m_length;
}

(6)線(xiàn)性表的清空

void clear()
{
  //清空線(xiàn)性表
  m_length = 0;
}

(7)[]操作符重載

//[]操作符重載
T& operator[](int index)
{
  //判斷目標(biāo)位置是否合法
  if((0 <= index) && (index < m_length))
  {
      //返回下標(biāo)相應(yīng)的元素
      return m_array[index];
  }
  else
  {
      THROW_EXCEPTION(IndexOutOfBoudsException, "Paramenter index is invalid...");
  }
}
//const對(duì)象的[]重載
T operator[](int index)const
{
  //轉(zhuǎn)換為非const對(duì)象后使用[]操作
  return (const_cast<SeqList<T>&>(*this))[index];
}

(8)順序存儲(chǔ)結(jié)構(gòu)空間的大小
virtual int capacity()const = 0;
由于存儲(chǔ)空間在子類(lèi)分配,因此為純虛函數(shù)。

3、順序存儲(chǔ)結(jié)構(gòu)的抽象實(shí)現(xiàn)

 template <typename T>
  class SeqList:public List<T>
  {
  public:
    bool insert(int index, const T& value)
    {
      //判斷目標(biāo)位置是否合法
      bool ret = (0 <= index) && (index <= m_length);
      ret = ret && ((m_length + 1) <= capacity());
      if(ret)
      {
          //將目標(biāo)位置后的所有元素后移一個(gè)位置
          for(int i = m_length -1; index <= i; i--)
          {
              m_array[i+1] = m_array[i];
          }
          //將新元素插入到目標(biāo)位置
          m_array[index] = value;
          //線(xiàn)性表長(zhǎng)度加1
          m_length++;
      }
      return ret;
    }
    bool remove(int index)
    {
      //判斷目標(biāo)位置是否合法
      bool ret = (0 <= index) && (index < m_length);
      if(ret)
      {
          //將目標(biāo)位置后的所有元素前移一位
          for(int i = index; i < m_length-1; i++)
          {
              m_array[i] = m_array[i+1];
          }
          //將線(xiàn)性表長(zhǎng)度減1
          m_length--;
      }
      return ret;
    }
    bool set(int index, const T& value)
    {
      //判斷目標(biāo)位置是否合法
      bool ret = (0 <= index) && (index < m_length);
      if(ret)
      {
          //修改目標(biāo)位置元素的值
          m_array[index] = value;
      }
      return ret;
    }
    bool get(int index, T& value)const
    {
      //判斷目標(biāo)位置是否合法
      bool ret = (0 <= index) && (index < m_length);
      if(ret)
      {
          //將目標(biāo)位置作為下標(biāo)獲取元素
          value = m_array[index];
      }
      return ret;
    }
    int length()const
    {
      //線(xiàn)性表長(zhǎng)度
      return m_length;
    }
    void clear()
    {
      //清空線(xiàn)性表
      m_length = 0;
    }

    int find(const T& value)const
    {
        int ret = -1;
        //遍歷線(xiàn)性表
        for(int i = 0; i < m_length; i++)
        {
            //如果找到元素,退出循環(huán)
            if(m_array[i] == value)
            {
               ret = i;
               break;
            }
        }
        return ret;
    }

    //[]操作符重載
    T& operator[](int index)
    {
      //判斷目標(biāo)位置是否合法
      if((0 <= index) && (index < m_length))
      {
          //返回下標(biāo)相應(yīng)的元素
          return m_array[index];
      }
      else
      {
          THROW_EXCEPTION(IndexOutOfBoudsException, "Paramenter index is invalid...");
      }
    }
    //const對(duì)象的[]重載
    T operator[](int index)const
    {
      //轉(zhuǎn)換為非const對(duì)象后使用[]操作
      return (const_cast<SeqList<T>&>(*this))[index];
    }
    virtual int capacity()const = 0;

  protected:
    T* m_array;//順序存儲(chǔ)空間
    int m_length;//當(dāng)前線(xiàn)性表的長(zhǎng)度
  };

4、順序存儲(chǔ)結(jié)構(gòu)中數(shù)據(jù)元素移動(dòng)的技巧

    數(shù)據(jù)元素的前移:
    將后面的數(shù)據(jù)元素向前移動(dòng),需要先將前面的數(shù)據(jù)元素前移,依次移動(dòng),直到最后一個(gè)數(shù)據(jù)元素前移,一般用于刪除一個(gè)數(shù)據(jù)元素后將后面的數(shù)據(jù)元素前移。
  //將目標(biāo)位置后的所有元素前移一位
  for(int i = index; i < m_length-1; i++)
  {
      m_array[i] = m_array[i+1];
  }
    數(shù)據(jù)元素的后移:
    將前面的數(shù)據(jù)元素向后移動(dòng),需要先將最后的數(shù)據(jù)元素后移,依次移動(dòng),直到第i個(gè)數(shù)據(jù)元素被后移,一般用于插入一個(gè)新的數(shù)據(jù)元素,需要先將插入位置后的所有數(shù)據(jù)元素后移,在位置處放入新的數(shù)據(jù)元素。
  //將目標(biāo)位置后的所有元素后移一個(gè)位置
  for(int i = m_length -1; index <= i; i--)
  {
      m_array[i+1] = m_array[i];
  }

5、原生數(shù)組實(shí)現(xiàn)的線(xiàn)性表

    使用原生數(shù)組作為順序存儲(chǔ)空間,使用模板參數(shù)確定數(shù)組大小。
 template <typename T, int N>
  class StaticList:public SeqList<T>
  {
  public:
    StaticList()
    {
      this->m_array = m_space;//指定父類(lèi)指針指向的空間
      this->m_length = 0;//設(shè)置初始長(zhǎng)度
    }
    int capacity() const
    {
      return N;
    }
  protected:
    T m_space[N];//順序存儲(chǔ)空間,N為模板參數(shù)
  };
    需要父類(lèi)的實(shí)現(xiàn)純虛函數(shù)capacity()。

6、動(dòng)態(tài)分配空間實(shí)現(xiàn)的線(xiàn)性表

        使用動(dòng)態(tài)申請(qǐng)的堆空間作為順序存儲(chǔ)空間,動(dòng)態(tài)設(shè)置順序存儲(chǔ)空間的大小并確保重置順序存儲(chǔ)空間大小時(shí)的異常安全。

函數(shù)異常安全要求不泄漏任何資源,不允許破壞數(shù)據(jù)。為了確保異常安全,在異常拋出時(shí),必須確保:
A、對(duì)象內(nèi)的任何成員仍然能保持有效狀態(tài)
B、沒(méi)有數(shù)據(jù)的破壞及資源泄漏。

template <typename T>
class DynamicList:public SeqList<T>
{
public:
  DynamicList(int capacity)
  {
    //申請(qǐng)動(dòng)態(tài)空間
    this->m_array = new T[capacity];
    if(this->m_array)
      {
        this->m_length = 0;//初始長(zhǎng)度
        this->m_capacity = capacity;//空間大小
      }
    else
      {
        THROW_EXCEPTION(NoEnoughMemoryException, "No enough memory...");
      }
  }
  int capacity() const
  {
    return m_capacity;
  }

  void resize(int capacity)
  {
    if(capacity != m_capacity)
      {
        T* array = new T[capacity];
        if(array)
          {
            int length = (this->length() < capacity ? this->length():capacity);
            for(int i = 0; i < length; i++)
              {
                array[i] = this->m_array[i];
                //如果拋出異常,原數(shù)組狀態(tài)沒(méi)有改變
              }
            T* temp = this->m_array;
            this->m_array = array;
            this->m_capacity = capacity;
            this->m_length = length;
            delete[] temp;
            //如果拋出異常,重置后的數(shù)組狀態(tài)已經(jīng)改變
          }
        else
          {
            THROW_EXCEPTION(NoEnoughMemoryException, "No enough memory...");
          }
      }
  }
  ~DynamicList()
  {
    delete[] this->m_array;//釋放申請(qǐng)的動(dòng)態(tài)空間
  }
protected:
  int m_capacity;//順序存儲(chǔ)空間的大小
};

二、順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表的效率分析

1、順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表的時(shí)間復(fù)雜度分析

數(shù)據(jù)結(jié)構(gòu)(三)——基于順序存儲(chǔ)結(jié)構(gòu)的線(xiàn)性表

2、順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表的效率分析

順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表的插入和刪除操作的時(shí)間復(fù)雜度都是O(n),但是由于插入和刪除操作都會(huì)涉及到線(xiàn)性表中數(shù)據(jù)元素的移動(dòng),因此會(huì)頻繁涉及拷貝構(gòu)造函數(shù)和賦值操作符的調(diào)用,如果數(shù)據(jù)元素對(duì)象內(nèi)部的資源較多,對(duì)象間的復(fù)制、賦值將是非常耗時(shí)的,同時(shí)由于線(xiàn)性表是泛型模板,無(wú)法確定實(shí)際實(shí)例化的對(duì)象類(lèi)型是否是占有資源的類(lèi)類(lèi)型,因此需要禁用拷貝構(gòu)造函數(shù)和賦值操作符,禁用的方式只需要將拷貝構(gòu)造函數(shù)和賦值操作符聲明為protected即可。

template <typename T>
class List:public Object
{
protected:
  List(const List<T>& other);
  List<T>& operator=(const List<T>& other);
public:
  List(){}
  virtual bool insert(int index, const T& value) = 0;
  virtual bool remove(int index) = 0;
  virtual bool set(int index, const T& value) = 0;
  virtual bool get(int index, T& value) = 0;
  virtual int length()const = 0;
  virtual void clear() = 0;
};

3、順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表的缺陷

順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表重載了[]操作符,因此可以使用[]操作符訪問(wèn)順序存儲(chǔ)結(jié)構(gòu)線(xiàn)性表中的元素。但是線(xiàn)性表中必須存在要訪問(wèn)的元素,即先插入元素才能使用[]操作符訪問(wèn)元素。

三、數(shù)組類(lèi)的工程實(shí)現(xiàn)

1、數(shù)組類(lèi)的抽象實(shí)現(xiàn)

    要?jiǎng)?chuàng)建一個(gè)數(shù)組類(lèi)取代原生數(shù)組,數(shù)組類(lèi)需要避免原生數(shù)組的缺陷:

A、數(shù)組類(lèi)包含長(zhǎng)度信息
B、數(shù)組類(lèi)能夠主動(dòng)發(fā)現(xiàn)越界訪問(wèn)
數(shù)組類(lèi)的設(shè)計(jì)如下:
A、抽象類(lèi)模板,存儲(chǔ)空間的位置和大小由子類(lèi)完成
B、重載數(shù)組操作符,判斷訪問(wèn)下標(biāo)是否越界
C、提供數(shù)組長(zhǎng)度的抽象訪問(wèn)函數(shù)
D、拷貝構(gòu)造函數(shù)和賦值操作符需要在子類(lèi)實(shí)現(xiàn)
數(shù)組的實(shí)現(xiàn):

template <typename T>
  class Array:public Object
  {
  public:
    virtual bool set(int index, const T& value)
    {
      bool ret = (0 <= index) && (index < length());
      if(ret)
      {
          m_array[index] = value;
      }
      return ret;
    }
    virtual bool get(int index, T& value)
    {
      bool ret = (0 <= index) && (index < length());
      if(ret)
      {
          value = m_array[index];
      }
      return ret;
    }

    T& operator[](int index)
    {
      if((0 <= index) && (index < length()))
      {
          return m_array[index];
      }
      else
      {
          THROW_EXCEPTION(IndexOutOfBoudsException, "Parameter index is valid...");
      }
    }
    T operator[](int index)const
    {
      return const_cast<T&>(*this)[index];
    }

    virtual int length()const = 0;
  protected:
    T* m_array;
  };
}

2、靜態(tài)數(shù)組類(lèi)實(shí)現(xiàn)

指定原生數(shù)組作為數(shù)組類(lèi)的存儲(chǔ)空間實(shí)現(xiàn)靜態(tài)數(shù)組類(lèi),使用模板參數(shù)指定數(shù)組大小,實(shí)現(xiàn)函數(shù)返回?cái)?shù)組的長(zhǎng)度,實(shí)現(xiàn)重載拷貝構(gòu)造函數(shù)和賦值操作符。

template &lt;typename T,int N&gt;
class StaticArray:public Array&lt;T&gt;
{
public:
StaticArray()
{
this-&gt;m_array = m_space;
}
//拷貝構(gòu)造函數(shù)
StaticArray(const StaticArray&lt;T,N&gt;& other)
{
this-&gt;m_array = m_space;
for(int i = 0; i &lt; N; i++)
{
m_space[i] = other.m_space[i];
}
}
//賦值操作符
StaticArray& operator=(const StaticArray&lt;T,N&gt;& other)
{
if(this != &other)
{
for(int i = 0; i&lt; N; i++)
{
m_space[i] = other.m_space[i];
}
}
return *this;
}
int length() const
{
return N;
}
protected:
T m_space[N];//存儲(chǔ)空間
};

3、動(dòng)態(tài)分配數(shù)組實(shí)現(xiàn)

  使用動(dòng)態(tài)分配的堆空間作為數(shù)組類(lèi)的存儲(chǔ)空間實(shí)現(xiàn)動(dòng)態(tài)分配數(shù)組類(lèi)。
  類(lèi)模板設(shè)計(jì)需要?jiǎng)討B(tài)確定分配存儲(chǔ)空間的大小,實(shí)現(xiàn)函數(shù)返回?cái)?shù)組大小,實(shí)現(xiàn)拷貝構(gòu)造函數(shù)和賦值操作符。

template &lt;typename T&gt;
class DynamicArray:public Array&lt;T&gt;
{
public:
//構(gòu)造函數(shù)
DynamicArray(int length)
{
this-&gt;m_array = new T[length];
if(this-&gt;m_array != NULL)
{
this-&gt;m_length = length;
}
else
{
THROW_EXCEPTION(NoEnoughMemoryException, "No enough memory...");
}
}
//拷貝構(gòu)造函數(shù)
DynamicArray(const DynamicArray&lt;T&gt;& other)
{
this-&gt;m_array = new T[other.m_length];
if(this-&gt;m_array != NULL)
{
this-&gt;m_length = other.m_length;
}
else
{
THROW_EXCEPTION(NoEnoughMemoryException, "No enough memory...");
}
}
//賦值操作符
DynamicArray&lt;T&gt;& operator=(const DynamicArray&lt;T&gt;& other)
{
if(this != &other)
{
T* array = new T[other.m_length];
if(array != NULL)
{
for(int i = 0; i &lt; other.m_length; i++)
{
array[i] = other.m_array[i];
}
T* temp = this-&gt;m_array;
this-&gt;m_array = array;
this-&gt;m_length = other.m_length;
delete[] temp;
}
else
{
THROW_EXCEPTION(NoEnoughMemoryException, "No enough memory...");
}
}
return *this;
}

int length()const
{
  return m_length;
}
//重置數(shù)組長(zhǎng)度
void resize(int length)
{
  if(this->m_length != length)
  {
      T* array = new T[length];
      if(array != NULL)
      {
          int size = (length < this->m_length)?length:this->m_length;
          for(int i = 0; i < size; i++)
          {
              array[i] = this->m_array[i];
          }
          T* temp = this->m_array;
          this->m_array = array;
          this->m_length = length;
          delete[] temp;
      }
      else
      {
          THROW_EXCEPTION(NoEnoughMemoryException, "No enough memory...");
      }
  }
}
~DynamicArray()
{
  delete[] this->m_array;
}

protected:
int m_length;//數(shù)組長(zhǎng)度
};

網(wǎng)站欄目:數(shù)據(jù)結(jié)構(gòu)(三)——基于順序存儲(chǔ)結(jié)構(gòu)的線(xiàn)性表
路徑分享:http://chinadenli.net/article42/gppjhc.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供網(wǎng)站建設(shè)、靜態(tài)網(wǎng)站網(wǎng)站收錄、網(wǎng)站導(dǎo)航定制開(kāi)發(fā)、網(wǎng)頁(yè)設(shè)計(jì)公司

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶(hù)投稿、用戶(hù)轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話(huà):028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來(lái)源: 創(chuàng)新互聯(lián)

網(wǎng)站優(yōu)化排名