8

アプリケーションで継続的なリークが見つかりました。メモリ プロファイラーを使用して調べたところ、コースが Microsoft Speech.Synthesizer のオブジェクトであることがわかりました。

そこで、仮説を検証するおもちゃのプロジェクトを作成します。

// Speech.Synthesizer オブジェクトのメモリ リークを示すおもちゃの例

static void Main(string[] args)
{
    string text = "hello world. This is a long sentence";
    PromptBuilder pb = new PromptBuilder();
    pb.StartStyle(new PromptStyle(PromptRate.ExtraFast));
    pb.AppendText(text);
    pb.EndStyle();
    SpeechSynthesizer tts = new SpeechSynthesizer();

while (true)
{
    //SpeechSynthesizer tts = new SpeechSynthesizer();
    Console.WriteLine("Speaking..."); 
    tts.Speak(pb);

    //Print private working set sieze
    Console.WriteLine("Memory: {0} KB\n", (Process.GetCurrentProcess().PrivateMemorySize64 / 1024).ToString("0"));

    //tts.Dispose();    //also this doesn't work as well
    //tts = null;

    GC.Collect();   //a little help, but still leaks
}
}

その結果、メモリ リークが Speech.Synthesizer によるものであることが実際に確認されました。

Speaking...

メモリー: 42184KB

話している... メモリ: 42312 KB

話している... メモリ: 42440 KB

話している... メモリ: 42568 KB

話している... メモリ: 42696 KB

話している... メモリ: 42824 KB

話している... メモリ: 43016 KB

話している... メモリ: 43372 KB

私はそれをグーグルで検索し、他の多くの人が同じ問題に遭遇したことを発見しました: 1: SpeechSynthesizerの一定のメモリ リーク-リーク

しかし、悲しいことに、私はそれに対する解決策を見つけられませんでした。ずいぶん前に質問された問題なので、解決されたかどうかお聞きしたいです。

どうもありがとう。

アップデート:

.Net Speech.Synthesizer パッケージではなく SAPI COM dll を使用するように切り替えると (基本的には同じものですが)、メモリ リークが停止します。

2 つの呼び出し動作 (SAPI dll と .net Speech パッケージ) のメモリ動作が異なるのはなぜですか? 後者は、以前の SAPI dll のラッパーにすぎないようです。

    static void Test2()
{
    //SAPI COM component this time
    SpeechLib.SpVoiceClass tts = new SpeechLib.SpVoiceClass();
    tts.SetRate(5);
    string text = "hello world. This is a long sentence";
    //tts.Speak("helloWorld", SpeechLib.SpeechVoiceSpeakFlags.SVSFDefault);
while (true)
{

    Console.WriteLine("Speaking...");
    tts.Speak(text, SpeechLib.SpeechVoiceSpeakFlags.SVSFDefault);

    //Print private working set sieze
    Console.WriteLine("Memory: {0} KB\n", (Process.GetCurrentProcess().PrivateMemorySize64 / 1024).ToString("0"));

    GC.Collect();
}

}

メモリ: 32044 KB

話している... メモリ: 32044 KB

話している... メモリ: 32044 KB

話している... メモリ: 32044 KB

話している... メモリ: 32044 KB

話している... メモリ: 32044 KB

話している... メモリ: 32044 KB

話している... メモリ: 32044 KB

4

3 に答える 3

4

最終的解決:

関連するキーワードをGoogleで検索すると、実際にはMicrosoftのバグであることがわかります。

.Net Speech.Synthesizer パッケージではなく SAPI COM dll を使用するように切り替えている間 (基本的には同じものですが)、メモリのリークが停止するようです。

于 2012-06-26T21:01:12.800 に答える
3

SpeechSynthesizer のすべての詳細はわかりませんが、ここで使い捨てパターンを使用してみてください。SpeechSynthesizer はIDisposableを実装しているため、

コードは次のようになります。

while (true)
{
   using (SpeechSynthesizer tts = new SpeechSynthesizer())
   {
      Console.WriteLine("Speaking..."); 
      tts.Speak(pb);

      //Print private working set sieze
      Console.WriteLine("Memory: {0} KB\n",(Process.GetCurrentProcess().PrivateMemorySize64 / 1024).ToString("0"));
   }
}

これが Microsoft の例と非常によく似ていることに気付いた場合は、こちら

これは実際にはメモリ リークのようです。Microsoft.Speech ランタイムを使用してみましたか? 構文は非常によく似ており、同じ問題は発生しないはずであると述べています。

于 2012-05-22T18:15:23.440 に答える