反转双向链表的前向互易失败

时间:2014-01-22 16:50:23

标签: c++ pointers linked-list

我正在处理一个名为Reverse()的函数,我只使用两个链接来反转列表中元素的顺序。我已经搜索了许多方法来做到这一点,但它始终以“分段错误”结束。我有一个方法可以帮助指出出错的地方,但它能告诉我的最多的是当我创建一个包含五个元素的列表(不包括头部和尾部)时,“位置0处存在”向前互易失败“。请记住,我不希望给我代码,而只是你对错误的看法。

void List<T>::Reverse ()                                                       
{                                                                              
  //make sure that the list is long enough                                     
  if( this->Empty())                                                           
    return;                                                                                                                                                                                                                            

  Link * link = this->head_;                                                   
  Link * temp = NULL;                                                          

  while( link != NULL )                                                        
  {                                                                              
    temp = link->next_;                                                        
    link->next_ = link->prev_;                                                 
    link->prev_ = temp;                                                        

    if( link->prev_ == NULL )                                                  
      head_ = link;                                                            

    link = link->prev_;                                                        
  }                                                                                 
  CheckLinks();                                                                
 }  

1 个答案:

答案 0 :(得分:1)

您的算法运行正常。该错误位于代码中的其他位置。

我创建了自己的(非常快速和肮脏的)双重链接列表来测试它 我在一个文件中完成了这一切。

我的链接结构与您的略有不同:

#include <iostream>

template <typename T>
struct Link
{
    Link (const T &data, Link <T> *prev = NULL, Link <T> *next = NULL) ;

    T data ;
    Link <T> *next_ ;
    Link <T> *prev_ ;
};

template <typename T>
Link <T>::Link (const T &data, Link <T> *prev, Link <T> *next) : data (data), prev_ (prev), next_ (next)
{
}

然后是我的测试列表结构:

template <typename T>
struct List
{
    List () ;

    bool IsEmpty () const ;
    void Reverse () ;
    void CheckLinks () const ;

    Link <T> *head_ ;
};

template <typename T>
List <T>::List () : head_ (NULL)
{
}

template <typename T>
bool List <T>::IsEmpty () const
{
    return head_ == NULL ;
}

template <typename T>
void List <T>::Reverse ()
{
    if (this->IsEmpty () == true) {
        return ;
    }

    Link <T> *link = head_ ;
    Link <T> *temp = NULL ;

    while (link != NULL) {
        temp = link->next_ ;
        link->next_ = link->prev_ ;
        link->prev_ = temp ;

        if (link->prev_ == NULL) {
            head_ = link ;
        }

        link = link->prev_ ;
    }
}

template <typename T>
void List <T>::CheckLinks () const
{
    Link <T> *link = head_ ;

    while (link != NULL) {
        std::cout << link->data << " " ;
        link = link->next_ ;
    }

    std::cout << std::endl ;
}

这些是我跑来测试以确保它是正确的测试。

// Null List
void Test0 ()
{
    List <int> list ;

    list.CheckLinks () ;
    list.Reverse () ;
    list.CheckLinks () ;
}

// List with 1 node
void Test1 ()
{
    Link <int> n1 (1) ;

    List <int> list ;
    list.head_ = &n1 ;

    list.CheckLinks () ;
    list.Reverse () ;
    list.CheckLinks () ;
}

// List with 2 nodes
void Test2 ()
{
    Link <int> n1 (1) ;
    Link <int> n2 (2) ;

    n1.next_ = &n2 ;
    n2.prev_ = &n1 ;

    List <int> list ;
    list.head_ = &n1 ;

    list.CheckLinks () ;
    list.Reverse () ;
    list.CheckLinks () ;
}

// List with 3 nodes
void Test3 ()
{
    Link <int> n1 (1) ;
    Link <int> n2 (2) ;
    Link <int> n3 (3) ;

    n1.next_ = &n2 ;

    n2.prev_ = &n1 ;
    n2.next_ = &n3 ;

    n3.prev_ = &n2 ;

    List <int> list ;
    list.head_ = &n1 ;

    list.CheckLinks () ;
    list.Reverse () ;
    list.CheckLinks () ;
}

// List with 4 nodes
void Test4 ()
{
    Link <int> n1 (1) ;
    Link <int> n2 (2) ;
    Link <int> n3 (3) ;
    Link <int> n4 (4) ;

    n1.next_ = &n2 ;

    n2.prev_ = &n1 ;
    n2.next_ = &n3 ;

    n3.prev_ = &n2 ;
    n3.next_ = &n4 ;

    n4.prev_ = &n3 ;

    List <int> list ;
    list.head_ = &n1 ;

    list.CheckLinks () ;
    list.Reverse () ;
    list.CheckLinks () ;
}

以下是我的主要内容:

int main (void) 
{
    Test0 () ;
    Test1 () ;
    Test2 () ;
    Test3 () ;
    Test4 () ;

    return 0 ;
}

希望这足以让你相信你的错误在其他地方。