2016-03-26 9 views
-3

tStack.exeの0x003165F0でスローされた例外:0xC0000005:0x9BFF07EFの場所を読み取っているアクセス違反。tStack.exeの0x003165F0でスローされた例外:0xC0000005:0x9BFF07EFの場所を読み取っているアクセス違反。

私はこのプログラムでこの問題を解決できないようです。私は別の場所でこのような読み取り/書き込みエラーを取得し続けます。ここで.cppファイルと.hの

.cppファイルは次のとおりです。

#include <stdio.h> 
#include <stdlib.h> 
#include "stack.h" 
#include <string> 
#include <iostream> 
//using namespace std; 

tStack::tStack() 
{ 
} 

tStack::~tStack() 
{ 
} 

tStack::tStack(const tStack &) 
{ 
} 

void tStack::Pop() 
{ 
    snode *tmp_ptr = NULL; 

    if (front) 
    { 

     tmp_ptr->next = front; 
     front = tmp_ptr; 
     free(tmp_ptr); 
    } 
    else 
     std::cout << "\nStack is Empty"; 
} 

void tStack::Push(std::string op) 
{ 
    snode *tmp_ptr = front; 

    tmp_ptr->data = op; 

    if (front) 
    { 
    tmp_ptr->next = front; 
    front = tmp_ptr; 
    } 
    else 
    { 
    front = tmp_ptr; 
    front->next = NULL; 
    } 
} 

void tStack::Print() 
{ 
    snode *cur_ptr = front; 

    if (cur_ptr) 
    { 
     std::cout << "\nElements in Stack:\n"; 
     while (cur_ptr) 
     { 
      std::cout << cur_ptr->data; 
      cur_ptr = cur_ptr->next; 
     } 
     std::cout << "\n"; 
    } 
    else 
     std::cout << "\nStack is Empty"; 
} 

void tStack::cStack() 
{ 
    free(front); 
} 

void tStack::convert(std::string postfix, tStack a) 
{ 
    int count = 0; 
    bool lastOper; 
    std::string pusher, val1, val2; 

    for (int i = 0; i < postfix.size(); i++) 
    { 
     if (isalpha(postfix[i])) 
     { 
      pusher = postfix[i]; 
      a.Push(pusher); 
      count++; 

     } 
     else 
     { 

      if (count < 2) 
      { 
       std::cout << "There are not enough values to perform an operation."; 
      } 

      else 
      { 
       pusher = postfix[i]; 
       val1 = front->data; 
       a.Pop(); 
       val2 = front->data; 
       a.Pop(); 
       a.Push(")"); 
       a.Push(val1); 
       a.Push(pusher); 
       a.Push(val2); 
       a.Push("("); 
      } 
      lastOper = true; 
     } 
    } 
} 

.H:

#pragma once 
#include <stdio.h> 
#include <stdlib.h> 
#include "stack.h" 
#include <string.h> 
#include <iostream> 
//using namespace std; 
class snode 
{ 
public: 
    std::string data; 
    snode *next; 
}; 
class tStack 
{ 
public: 
    tStack(); 
    ~tStack(); 
    tStack(const tStack &); 
    void Pop(); 
    void Push(std::string); 
    void Print(); 
    void cStack(); 
    void convert(std::string, tStack); 
private: 

    snode *front; 


}; 

私は名前空間stdを使用して使用していない示唆いくつかの記事を見つけましたが、それは助けていないようです。リンクされたリストがどのように機能するのかを完全に誤解していますか?

+1

あなたのポインタ数学がどこかオフになっています。どこでプログラムをデバッグする必要があります。 – Carcigenicate

+0

ありがとう、私のために何かをクリアすることができますか?私がfront-> next = temp_ptrと言うとき、フロントの次のポインタ値がtemp_ptrのポイントを指すことを意味すると思いますか? – Perkis

+0

他の誰かがすでに問題を発見したようです。アクセス違反エラーが発生した場合は、通常、アドレスの計算が間違っているか、メモリ管理が不十分であることを意味します。そして、申し訳ありませんが、私は指針を扱って以来、長いことでした。私はあなたを迷子にしたくありません。 – Carcigenicate

答えて

0

あなたのコードを一目見て、私はバグを発見しました。

front = tmp_ptr; 
free(tmp_ptr); 

このコードは意味がありません。実際にスタックの最上部に使用されているメモリを解放します。このような種類のバグを修正するのは簡単です。

+0

ありがとうございます。無料のメソッドまたはfront = tmp_ptrのみを参照していますか?同じように? – Perkis

+0

@Perkisのみ無料、あなたは古いフロントを覚えて、それを解放する – greenshade

0

あなたのコードを見ると、自家製のリンクリストを「スタック」方式で実装しようとしていると思います(最初から最後まで、あるいはその逆)。私が間違っているかどうか教えてください。

私はあなたのコードでいくつかの問題が見ることができます:メソッドがために実行したときに、それがNULLであることを保証することなく、あなたの「ポップ」の方法であなたは「フロント」メンバーを使用しようとしている。

問題1を初めて;それをNULLに割り当てる "tStack"のデフォルトのコンストラクタ内に定義を追加します。

問題2:あなたの "Pop"メソッドでは、リストから要素を削除し、追加しないようにしたいと思います。私は正しいですか?もしそうなら、あなたの "Pop"メソッドは正しく実装されていません。

void tStack::Pop() 
{ 
    if (front) 
    { 
     snode *tmp_ptr = front; 

     front = front->next; 


     free(tmp_ptr); 
    } 
    else 
     std::cout << "\nStack is Empty"; 
} 

注:ここではあなたの「ポップ」の方法の適切書かれたバージョンがある私は「スタック」としてあなたのリストを扱う方法で、このメソッドを実装しました。

このコードでは別の重要なトピックが表示されます。「snode」クラスのデフォルトのコンストラクタを定義して、自動的にその「次の」メンバをNULLに割り当てます。

問題3:「プッシュ」方法が正しく実装されていません。 "tmp_ptr"は新しいメモリに割り当てられ、リストの最初の要素には割り当てられません。

ライン:

snode *tmp_ptr = front; 

は次のようになります。

snode *tmp_ptr = new snode; 

注:あなたがこれを行うことによって、あなたの "プッシュ" 方式を短縮することができます

void tStack::Push(std::string op) 
{ 
    snode *tmp_ptr = new snode; 

    tmp_ptr->data = op; 

    tmp_ptr->next = front; 

    front = tmp_ptr; 
} 

注:このコードでは、t彼は "snode" s "next"メンバーは、次の要素がない場合、常にNULLに等しくなるでしょう。これは、あなたの "Snode"クラス用のカスタムデフォルトコンストラクタを実装することが良いことの1つの理由です。

問題4: "cStack"メソッドは、リストの各要素をループし、それぞれを個別に解放する必要があります。現在の実装では、最初の要素のみが解放されます。

アドバイス:ポインタを含む任意のクラスは、動的にそれが割り当てられたことを動的メモリをクリアするカスタムデストラクタを持って行うことができ、それはを所有しているというメモリを割り当てられています。これは、メソッドが外部ソースから動的メモリをクリアするために使用されている場合であっても、常にバックアップ計画を立てることができるため、適用可能です。

しかし、あなたのリスト要素の1つを "削除"すると削除される連鎖反応が設定されるため、このアドバイスはあなたの "snode"クラス(少なくとも "次の"メンバーではない)には当てはまりません以下のすべての要素。

これは、すべて私が見ることができる問題です。私の返信が助けになったら教えてください。 :)

EDIT:あなたの "TSTACK" クラスは空白のデフォルトコンストラクタがあります。これに

tStack::tStack() 
{ 
} 

変更を:

tStack::tStack() 
: front(NULL) 
{ 
} 

あなたのデフォルトのデストラクタがこれです:

tStack::~tStack() 
{ 
} 

これに変更してください:

tStack::~tStack() 
{ 
    // Clear the dynamic memory if needed. 
    if (front) 
     cStack(); 
} 

最後に、あなたの「Sノード」クラスにデフォルトコンストラクタを追加します。

snode::snode() 
: next(NULL) 
{ 
} 
+0

WOAH。ありがとうございました!あなたは私の質問に答えて、その後いくつか答えました! – Perkis

+0

コンストラクターやデストラクタのところまでは、まだ学習しています。リンクリストのための適切なコンストラクタとデストラクタを書くのに役立つリソースを知っていますか?私はすぐに漏れの束を持っているようです。また、どのようにしてb +をab +と同じように扱うことができるか知っていますか? – Perkis

+0

"resources"とは、リンクリストのリソースを具体的に、またはコンストラクタ/デストラクタの一般的な意味ですか?あなたにコンストラクタ/デストラクタについてどれだけ知っていますか?デフォルトのコンストラクタを自分のコードに配置しましたか、それとも他の誰かからコピーして貼り付けましたか?コードのほんの数行で動作するコンストラクタとデストラクタを与えることができますので、私は尋ねますが、私はあなたに何を伝えているかを理解したいと思います。あなたの2番目の質問で少し詳しく説明できますか?私はあなたが何を意味するのか正確には分かりません。 :\ – Fearnbuster

関連する問題