0

私は現在、RichTextbox のコンテンツをストリーム (現在 FileStream を使用) に保存し、他のデータと一緒にこれを行う方法を見つけようとしています。もちろん、このファイルからロードできるようにしたいです。私は現在、次の行に沿って何かを使用しようとしていました。

FileStream stream = new FileStream(); //this is actually correctly defined.
ASCIIEncoding encoding = new ASCIIEncoding();

//write Title
byte[] array = encoding.GetBytes(Title);
stream.WriteByte(Convert.ToByte(array.Length));
stream.Write(array, 0, array.Length);

//save textRange
textRange.Save(stream, System.Windows.DataFormats.Rtf);

//write Subtitle
byte[] array = encoding.GetBytes(Subtitle);
stream.WriteByte(Convert.ToByte(array.Length));
stream.Write(array, 0, array.Length);
//ect...and something very similar for Loading a file.

これは基本的に私がやろうとしていることです。私は実際に 2 つの TextRanges とさらに多くのプロパティを保存しています。したがって、私の問題は、 TextRange.Load() がファイルの最後まで読み取られることです...保存/ロードする必要がある2つの TextRanges があることを考えると、それを使用できなくなります。ここでは、RichTextBox のコンテンツを他のデータと共に保存/ロードできる別の方法を考え出そうとしています。ストリームを使用する必要はありません。私は実行可能な解決策に対してかなりオープンです。前もって感謝します!

〜ジェイソン

4

2 に答える 2

0

ファイルの最後までの読み取りに関する問題を解決するために、MemoryStream にロード/保存することができます。次のようになります。

  • ファイルをメモリにロードする
  • リッチテキストボックスの内容であるそのファイルのセクションを MemoryStream にロードします
  • そのMemoryStreamからリッチテキストボックスの内容をロードします

または、ファイルを作成および解析して、タイトル、コンテンツ、およびその他のフィールドのさまざまなセクションを含める方法を知りたいですか?

于 2009-03-27T05:39:33.443 に答える
0

現在のソリューションを投稿する必要があると考えました。それは完全にうまくいくようです。これを行う方法についてのヒントをくれた Chris と Ants に感謝します。

/// <summary>
    /// Reads a TextRange (DataFormats.Rtf) from the stream.
    /// </summary>
    /// <param name="stream">The stream to be read from.</param>
    /// <returns>The TextRange (DataFormats.Rtf) that was read from the stream.</returns>
    public static TextRange ReadTextRange(FileStream stream)
    {
        long startPos = stream.Position;
        int length = -1;
        int count = 0;
        int previousByte = 0;
        int currentByte = 0;
        //set previousByte to give the current one something to compare to
        previousByte = stream.ReadByte();
        //parse the file counting the { and } to find the end of the rtf portion of the file.
        while (count > 0 || length < 1)
        {
            length++;
            stream.Position = startPos + length;
            currentByte = stream.ReadByte();
            if (previousByte != 92) // not '\' so check to see if '{' or '}' is currentByte
            {
                if (currentByte == 123) // '{' increase count
                    count++;
                else if (currentByte == 125) // '}' decrease count
                    count--;
            }
            previousByte = currentByte;
        }
        //save finish position to move to later
        long finishPos = stream.Position;
        //reset stream position to start at beginning of rtf
        stream.Position = startPos;
        //read the rtf portion of the file into a byte[]
        byte[] content = new byte[length];
        stream.Read(content, 0, length);
        //put the byte[] into a memory stream
        MemoryStream memStream = new MemoryStream(content);
        FlowDocument doc = new FlowDocument();
        TextRange range = new TextRange(doc.ContentStart, doc.ContentEnd);
        //have the TextRange read from the memorystream
        range.Load(memStream, System.Windows.DataFormats.Rtf);
        memStream.Close();
        //set the position to after the rtf portion of the file
        stream.Position = finishPos;
        return range;
    }

この ReadTextRange メソッドは、FileStream からの読み取りを支援するために定義した StreamHelper クラスにあります。したがって、これはすべて、このように FileStream に保存されている TextRange をロードすることです...

//save query (TextRange)
        Query.Save(stream, System.Windows.DataFormats.Rtf);

誰かが同様の問題に遭遇した場合に、これが役立つことを願っています! :D

編集:

プロファイラーを使用したところ、このコードはあまり効率的ではないことがわかったので、いくつかの方法でこのコードをより効率的にするように変更しました。

  1. TextRange を使用する代わりに、MemoryStream memStream の内容を保持する byte[] を使用します。これにより範囲が切り取られます。多くの CPU を消費する負荷。

  2. ライン stream.Position = startPos + length を取り出したのは、最初の実行後に役に立たず、かなりの量の CPU を占有していることに気付いたからです。stream.Position--; を配置しました。行の後に previousByte = stream.ReadByte();

また、データ クラス内に UI 要素である TextRange を配置することで、自分が下手なコーダーであり、MVC に従っていないことに気付きました。今ではバイト[]があり、これははるかに優れています。

もう一度編集:

TextRange の代わりに byte[] を使用して数分後、byte[] のサイズがあることに気付いたので、解析する必要はありませんでした。代わりに、byte[] サイズを保存してから byte[] を保存します。これにより、非常に高速になり、非常に大きなファイルをほぼ瞬時に読み取ることができます。

于 2009-03-29T09:39:24.847 に答える