在分组的ListView中使用ItemTemplateSelector进行内存增长(泄漏?) [英] Memory growth ( leak? ) using ItemTemplateSelector in Grouped ListView

查看:53
本文介绍了在分组的ListView中使用ItemTemplateSelector进行内存增长(泄漏?)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个ListView将其分组.这些项目由图标表示,这些图标由ItemTemplateSelector选择.随着时间的流逝,我的应用程序的内存使用量不断增长.我的处理方式有天生的错误吗?

XAML

I have a ListView which groups it's items. The items are represented by icons, which are chosen by an ItemTemplateSelector. Over time, memory usage of my application grows. Is there something inherently wrong with the way I am doing things?

XAML

<Window x:Class="MemoryLeak.Window1"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="clr-namespace:MemoryLeak"
    Title="Window1" Height="300" Width="300">
  <Window.Resources>
    <local:IconSelector x:Key="iconSelector"/>

    <DataTemplate x:Key="_GoodIcon">
      <Rectangle Fill="LightGreen" Width="16" Height="16" Stroke="Black" StrokeThickness="1"/>
    </DataTemplate>

    <DataTemplate x:Key="_BadIcon">
      <Rectangle Fill="LightPink" Width="16" Height="16" Stroke="Black" StrokeThickness="1"/>
    </DataTemplate>

    <DataTemplate x:Key="_IndifferentIcon">
      <Rectangle Fill="LightCoral" Width="16" Height="16" Stroke="Black" StrokeThickness="1"/>
    </DataTemplate>

  </Window.Resources>
  <ListBox x:Name="_List" 
           VirtualizingStackPanel.IsVirtualizing="False" 
           ItemTemplateSelector="{StaticResource iconSelector}">
    <ListBox.GroupStyle>
      <GroupStyle>
        <GroupStyle.ContainerStyle>
          <Style TargetType="{x:Type GroupItem}">
            <Setter Property="Template">
              <Setter.Value>
                <ControlTemplate TargetType="{x:Type GroupItem}">
                  <ItemsPresenter/>
                </ControlTemplate>
              </Setter.Value>
            </Setter>
          </Style>
        </GroupStyle.ContainerStyle>
      </GroupStyle>
    </ListBox.GroupStyle>
  </ListBox>
</Window>



C#



C#

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Threading;

namespace MemoryLeak
{
  public partial class Window1 : Window
  {
    List<Item> _Items = new List<Item>();
    public Window1()
    {
      InitializeComponent();
      for (int ix = 0; ix < 20; ix++)
      {
        _Items.Add(new Item() { Name = string.Format("Item {0}", ix + 1), Location = "Here" });
      }
      CollectionViewSource cvs = new CollectionViewSource();
      cvs.GroupDescriptions.Add(new PropertyGroupDescription() { PropertyName = "Location" });
      cvs.Source = _Items;
      _List.ItemsSource = cvs.View;
      DispatcherTimer dt = new DispatcherTimer() { Interval = TimeSpan.FromMilliseconds(20) };
      dt.Tick += new EventHandler(dt_Tick);
      dt.Start();
    }

    public delegate void DispatchHandler();

    State currentState = State.Indifferent;
    void dt_Tick(object sender, EventArgs e)
    {
      currentState = (State)(((int)currentState + 1) % 3);
      IEditableCollectionView iecv = CollectionViewSource.GetDefaultView(_List.Items) as IEditableCollectionView;
      _Items.ForEach(i => { i.State = currentState; iecv.EditItem(i);  });
      iecv.CommitEdit();
    }
  }

  public enum State { Good, Bad, Indifferent };
  public class Item : INotifyPropertyChanged
  {
    public event PropertyChangedEventHandler PropertyChanged;
    PropertyChangedEventArgs e = new PropertyChangedEventArgs("State");
    State _State;
    public State State
    {
      get { return _State; }
      set
      {
        _State = value;
        if (PropertyChanged != null) PropertyChanged(this, e);
      }
    }
    public string Location { get; set; }
    public string Name { get; set; }
  }

  public class IconSelector : DataTemplateSelector
  {
    FrameworkElement _FeContext = null;
    Dictionary<State, DataTemplate> _IconTemplates = new Dictionary<State, DataTemplate>();
    void Init(FrameworkElement fe)
    {
      if (_FeContext == null && fe != null)
      {
        _IconTemplates[State.Good] = fe.FindResource("_GoodIcon") as DataTemplate;
        _IconTemplates[State.Bad] = fe.FindResource("_BadIcon") as DataTemplate;
        _IconTemplates[State.Indifferent] = fe.FindResource("_IndifferentIcon") as DataTemplate;
        _FeContext = fe;
      }
    }
    public override DataTemplate SelectTemplate(object item, DependencyObject container)
    {
      Init(container as FrameworkElement);
      DataTemplate dt;
      if (_IconTemplates.TryGetValue((item as Item).State, out dt))
      {
        return dt;
      }
      return base.SelectTemplate(item, container);
    }
  }
}

推荐答案

Hello John,

您的OS/Service Pack/.NET Framework(SP)版本是什么?

您运行应用程序多长时间了?您如何观察应用程序的内存使用情况(例如您使用的是什么工具)?该应用程序正在使用多少内存?

如果最小化应用程序窗口并等待一分钟左右,您是否可以观察到该应用程序的内存使用量减少?

看到内存使用量增加并不一定意味着有泄漏,因此请提供有关此问题的更多信息.论坛中的="=" http://msdn.microsoft.com/en-us/subscriptions/aa974230.aspx> MSDN订阅者支持
如果您对我们的支持有任何反馈,请联系 msdnmg@microsoft.com
Hello John,

What's your OS/Service Pack/.NET Framework (SP) version?

How long did you run the application? How did you observe the application's memory usage (like what tool did you use)? How much memory did the application was using?

And if you minimize the application window(s) and wait for a minute or so, can you observe a decrease of memory usage of the application?

Seeing memory usage increase doesn't necessarily mean there is a leak, so please provide more information on this issue.

Thanks,
Jie
MSDN Subscriber Support in Forum
If you have any feedback on our support, please contact msdnmg@microsoft.com


这篇关于在分组的ListView中使用ItemTemplateSelector进行内存增长(泄漏?)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆