2016-09-13 7 views
3

シリアライズ/デシリアライズ時にスタック内の要素の順序が逆になる問題があります。 REPROのために、このデモを参照してください。Newtonsoft.Jsonでシリアライズおよびデシリアライズした後、スタック要素の順序が逆になる

using System; 
using System.Collections.Generic; 
using Newtonsoft.Json; 

namespace StackChecker 
{ 
    class Program 
    { 
     enum Screen 
     { 
      Unknown, 
      Bypass, 
      ClaimDetails, 
      ClaimSearch, 
      ClaimSearchResults, 
      PatientSearchResults 
     } 

     static void Main(string[] args) 
     { 
      var screens = new Stack<Screen>(); 
      screens.Push(Screen.Unknown); 
      screens.Push(Screen.Bypass); 
      screens.Push(Screen.ClaimDetails); 
      screens.Push(Screen.ClaimSearch); 
      screens.Push(Screen.ClaimSearchResults); 
      screens.Push(Screen.PatientSearchResults); 

      foreach (var screen in screens) 
      { 
       Console.WriteLine("Screen {0}: {1}", (int)screen, screen); 
      } 

      var screenJson = JsonConvert.SerializeObject(screens); 
      Console.WriteLine("Screens Json: \"{0}\"", screenJson); 

      var screens2 = JsonConvert.DeserializeObject<Stack<Screen>>(screenJson); 
      foreach (var screen in screens2) 
      { 
       Console.WriteLine("Screen {0}: {1}", (int)screen, screen); 
      } 

      var screenJson2 = JsonConvert.SerializeObject(screens2); 
      Console.WriteLine("Screens Json: \"{0}\"", screenJson2); 

      Console.ReadLine(); 
     } 
    } 
} 

これは、次のように出力します

Screen 5: PatientSearchResults 
Screen 4: ClaimSearchResults 
Screen 3: ClaimSearch 
Screen 2: ClaimDetails 
Screen 1: Bypass 
Screen 0: Unknown 
Screens Json: "[5,4,3,2,1,0]" 
Screen 0: Unknown 
Screen 1: Bypass 
Screen 2: ClaimDetails 
Screen 3: ClaimSearch 
Screen 4: ClaimSearchResults 
Screen 5: PatientSearchResults 
Screens Json: "[0,1,2,3,4,5]" 

ので、疑問がある - なぜ順序が逆転していますか? (私も配列でこれを試して、配列の要素が反転していないことを証明することができます)

これは避けることができますか?
もしそうでなければ、誰もが優雅な回避策のアイディアを得ましたか?

+3

ここでシリアル化は問題になりません。次のコードを書くと、 'var s1 = new Stack (new [] {0,1,2,3,4}); var s2 = new Stack (')と同じ問題が発生します。 'IEnumerable'パラメータが与えられたときに' Stack'コンストラクタがどのように記述されるかが原因です。修正?スタックを構築する前にリストに逆シリアル化して逆にする? – spender

+2

'Stack 'のデフォルトの列挙子は、スタックからポップされる順序で項目を列挙します。その順序で別のスタックに項目をプッシュすると、もう一方のスタックにはその項目が逆順に格納されます。 –

答えて

1

Listにデシリアライズすると、var screens2 = JsonConvert.DeserializeObject<List<Screen>>(screenJson)のようになります。スタックをデータ構造として必要とする場合は、一時的なリストを作成してスタックに戻してコピーすることができます。

var screensTemp = JsonConvert.DeserializeObject<List<Screen>>(screenJson); 
screensTemp.Reverse(); 
var screens2 = new Stack<Screen>(screensTemp); 
foreach (var screen in screens2) 
{ 
    Console.WriteLine("Screen {0}: {1}", (int)screen, screen); 
} 
+0

重複した質問のお詫び - 投稿前にこの問題を検索しました。誰も助けてくれてありがとう:) –

関連する問題