简体   繁体   English

为什么WPF应用程序中的对象数目增加了?

[英]Why is the number objects in my WPF application increasing?

i write some code that reads a CSV file and convert it into a DateTable. 我写了一些读取CSV文件并将其转换为DateTable的代码。 In the next step it read the DataTable to get specific values. 在下一步中,它读取DataTable以获取特定值。 These values were saved in an object and this object will add to an ObserableCollection. 这些值保存在一个对象中,并且该对象将添加到ObserableCollection中。

XAML: XAML:

<ListView ItemsSource="{Binding ProdOrderView}" x:Name="listView"    Margin="9,70,112,34" AlternationCount="2" FontSize="14">
            <ListView.ItemContainerStyle>
                <Style TargetType="{x:Type ListViewItem}">
                    <Setter Property="HorizontalContentAlignment" Value="Stretch"/>
                    <Style.Triggers>
                        <Trigger Property="ItemsControl.AlternationIndex"  Value="0">
                            <Setter Property="Background" Value="White" />
                        </Trigger>
                        <Trigger Property="ItemsControl.AlternationIndex"  Value="1">
                            <Setter Property="Background" Value="LightGray" />
                        </Trigger>
                    </Style.Triggers>
                </Style>
            </ListView.ItemContainerStyle>
            <ListView.View >
                <GridView >
                    <GridViewColumn  Header="Fauf" Width="Auto">
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock  Text="{Binding Fauf}" TextAlignment="Right" Name="fauf"/>
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                    <GridViewColumn  Header="Prod-Start" Width="Auto">
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock  Text="{Binding Start}" TextAlignment="Center" Name="start"/>
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                    <GridViewColumn Header="Rück- &#xa;stand" Width="Auto">
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock x:Name="inRueck"  Text="{Binding InRueck}" TextAlignment="Center" />
                                <DataTemplate.Triggers>
                                    <DataTrigger Binding="{Binding InRueck, Converter={StaticResource ColorConverterInRueck}}" Value="delay">
                                        <Setter TargetName="inRueck" Property="Background" Value="Red" />
                                    </DataTrigger>
                                    <DataTrigger Binding="{Binding InRueck, Converter={StaticResource ColorConverterInRueck}}" Value="inTime">
                                        <Setter TargetName="inRueck" Property="Background" Value="Green" />
                                    </DataTrigger>
                                </DataTemplate.Triggers>
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                    <GridViewColumn Header="heute" Width="Auto"  >
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock x:Name="Heute" Text="{Binding Heute}" TextAlignment="Center" />
                                <DataTemplate.Triggers>
                                    <DataTrigger Binding="{Binding Heute}" Value="X">
                                        <Setter TargetName="Heute" Property="Background" Value="CornflowerBlue" />
                                    </DataTrigger>
                                    <DataTrigger Binding="{Binding Heute}" Value="?">
                                        <Setter TargetName="Heute" Property="Foreground" Value="DarkViolet" />
                                    </DataTrigger>
                                </DataTemplate.Triggers>
                            </DataTemplate>

                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                    <GridViewColumn Header="morgen" Width="Auto" >
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock  Text="{Binding Morgen}" TextAlignment="Center" Name="Morgen"/>
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                    <GridViewColumn Header="+2" Width="Auto" >
                        <GridViewColumn.CellTemplate>
                            <DataTemplate>
                                <TextBlock  Text="{Binding Uebermorgen}" TextAlignment="Center" Name="Uebermorgen"/>
                            </DataTemplate>
                        </GridViewColumn.CellTemplate>
                    </GridViewColumn>
                ...

                </GridView>
            </ListView.View>
        </ListView> 

Code-behind: 后台代码:

 public MainWindow()
    {
        InitializeComponent();
        MainViewModel mvm = new MainViewModel(filepath,pline);
        listView.ItemSource = mvm.ProdOrderView;
    }

MainViewModel: MainViewModel:

class MainViewModel
{
    #region Private Felder
    private ObservableCollection<ProductionOrder> _prodOrderList;

    private ListCollectionView _prodOrderView;
    #endregion

    #region Konstruktor
    public MainViewModel(string filepath, string pline)
    {
        // ProductionOrderliste initialisieren
        _prodOrderList = new ObservableCollection<ProductionOrder>();           

        _prodOrderList.Clear();
        fillObject(filepath, pline, ref _prodOrderList);

        // ListCollectionView initialisieren
        _prodOrderView = new ListCollectionView(_prodOrderList);

    }

    #endregion

    #region Öffentliche Eigenschaften
    public ListCollectionView ProdOrderView
    {
        get { return _prodOrderView; }
    }


    #endregion

    #region ConvertCSVtoDataTabble
    public DataTable ConvertCSVtoDataTable(string filename)
    {
        //DataTable anlegen
        DataTable dataTable = new DataTable();
        dataTable.Columns.Clear();
        dataTable.Rows.Clear();
        dataTable.Clear();

        try
        {
            //Filestream anlegen, dadurch kann Datei auch gelesen werden, wenn sie geöffnet ist
            FileStream logFileStream = new FileStream(filename, FileMode.Open, FileAccess.Read, FileShare.ReadWrite);

            using (StreamReader streamReader = new StreamReader(logFileStream))
            {
                //Array mit allen Überschriften
                string[] headers = streamReader.ReadLine().Split(';');
                //Schleife durchläuft das Array headers
                foreach (string header in headers)
                {
                    //Der DataTable wird eine Spalte mit dem aktuellen header (Überschrift) hinzugefügt.
                    dataTable.Columns.Add(header);
                }
                //Schleife, die so lange gültig ist bis das Ende des Streams erreicht wurde
                while (!streamReader.EndOfStream)
                {
                    //Array mit allen Zeilen füllen
                    string[] rows = streamReader.ReadLine().Split(';');


                    //Der DataTable wird die Zeile mit dem aktuellen Werten der Zeile hinzugefügt.
                    dataTable.Rows.Add(rows);
                }
                //StreamReader wird geschlossen
                streamReader.Close();
                //Filestream wird geschlossen
                logFileStream.Close();
            }
        }
        catch(IndexOutOfRangeException e)
        {
            Console.WriteLine("Fehlercode:" + e);
            ConvertCSVtoDataTable(filename);
        }
            //gefüllte DataTable wird zurückgegeben
            return dataTable;

        }

    #endregion

    #region fillObbject
    public void fillObject(string filepath, string plinie, ref ObservableCollection<ProductionOrder> liste)
    {
        //DataTable res = new DataTable();
        //res.Columns.Clear();
        //res.Rows.Clear();
        //res.Clear();


        string emptyField = "\" \"";
        DataTable res = ConvertCSVtoDataTable(filepath);
        try
        {
            foreach (DataRow row in res.Rows) // Loop over the rows.
            {


                if (row["AFKO_PLTXT"].ToString() == plinie)
                {

                    ////Objekt anlegen
                    ProductionOrder order = new ProductionOrder();

                    //#region Prüft ob Sammelhinweis vorhanden
                    string sammel = "";
                    Queue<string> queue = new Queue<string>();

                    if (res.Columns.Contains("ZZTAG_MO"))
                    {
                        //Montag
                        if (row["ZZTAG_MO"].ToString() == "X")
                        {
                            sammel = "MO";
                            queue.Enqueue(sammel);
                        }
                        //Dienstag
                        if (row["ZZTAG_DI"].ToString() == "X")
                        {
                            sammel = "DI";
                            queue.Enqueue(sammel);
                        }
                        //Mittwoch
                        if (row["ZZTAG_MI"].ToString() == "X")
                        {
                            sammel = "MI";
                            queue.Enqueue(sammel);
                        }
                        //Donnerstag
                        if (row["ZZTAG_DO"].ToString() == "X")
                        {
                            sammel = "DO";
                            queue.Enqueue(sammel);
                        }
                        //Freitag
                        if (row["ZZTAG_FR"].ToString() == "X")
                        {
                            sammel = "FR";
                            queue.Enqueue(sammel);
                        }
                        //Samstag
                        if (row["ZZTAG_SA"].ToString() == "X")
                        {
                            sammel = "SA";
                            queue.Enqueue(sammel);
                        }
                        //Sonntag
                        if (row["ZZTAG_SO"].ToString() == "X")
                        {
                            sammel = "SO";
                            queue.Enqueue(sammel);
                        }


                    }
                    // string sammelList wird zusammengesetzt
                    string sammelList = "";
                    if (queue.Count > 0)
                    {
                        sammelList = "/";
                        while (queue.Count > 0)
                        {
                            if (queue.Count > 1)
                                sammelList += queue.Dequeue() + "+";
                            else
                            {
                                sammelList += queue.Dequeue();
                            }
                        }
                    }
                    #endregion
                    //das Objekt wird mit den entsprechenden Werten gefüllt
                    order.Fauf = row["EXTRA_APO"].ToString();
                    order.Start = row["GSTRP_KO"].ToString();
                    order.Vorgang = row["LTXA1_AFVC"].ToString();
                    order.Kundenauftrag = row["KDAUF_FK"].ToString() + sammelList;
                    order.Material = row["MATNR_PO"].ToString();
                    order.Materialbezeichnung = row["MAKTX_MAKT"].ToString();
                    order.Menge = row["AFKO_GAMNG"].ToString();
                    order.WE_Menge = row["WEMNG_PO"].ToString();
                    order.Ende = row["GLTRP_KO"].ToString();
                    order.Notiz = row["NOTIZ_TEXT"].ToString();
                    order.Ladedatum = row["LDDAT_VBEP"].ToString();
                    order.Dauer = row["FAUFDAUER_REST_KO"].ToString();

                    //führende Nullen werden entfernt falls vorhanden
                    order.Kundenauftrag = order.Kundenauftrag.TrimStart('0');
                    order.Material = order.Material.TrimStart('0');

                    if (order.Menge.Contains(","))
                    {
                        order.Menge = order.Menge.Remove(order.Menge.IndexOf(@","));
                    }
                    if (order.WE_Menge.Contains(","))
                    {
                        order.WE_Menge = order.WE_Menge.Remove(order.WE_Menge.IndexOf(@","));
                    }
                    order.Heute = "";
                    order.Morgen = "";
                    order.Uebermorgen = "";
                    order.Plus3 = "";
                    order.Plus4 = "";
                    order.Plus5 = "";

                    string inKlaerung = "";

                    //konvertiert String zu Datetime
                    DateTime newStartDate = convertDateTime(order.Start);
                    order.Start = newStartDate.ToString("dd.MM.yyyy");


                    //Berechne Verzug in Tagen
                    int verzugTage = (DateTime.Today - newStartDate).Days;
                    order.InRueck = verzugTage.ToString();

                    //konvertiert String zu Datetime
                    var newLadedatum = convertDateTime(order.Ladedatum);
                    order.Ladedatum = newLadedatum.ToString("dd.MM.yyyy");
                    if (inKlaerung != emptyField)
                    {
                        //X in der Spalte setzen, an dem Tag wo es gefertigt wird
                        if (verzugTage >= 0)
                        {
                            order.Heute = "X";
                        }
                        else
                        {
                            switch (verzugTage)
                            {
                                case -1:
                                    order.Morgen = "X";
                                    break;
                                case -2:
                                    order.Uebermorgen = "X";
                                    break;
                                case -3:
                                    order.Plus3 = "X";
                                    break;
                                case -4:
                                    order.Plus4 = "X";
                                    break;
                                case -5:
                                    order.Plus5 = "X";
                                    break;
                                default:
                                    break;
                            }

                        }
                    }
                    else
                    {
                        order.Heute = "?";
                    }
                    try
                    {
                        //konvertiert String zu Datetime
                        var newEndDate = convertDateTime(order.Ende);
                        order.Ende = newEndDate.ToString("dd.MM.yyyy");
                    }
                    catch (FormatException e)
                    {
                        Console.WriteLine("Fehlercode:" + e);
                        order.Ende = "Fehler";
                    }

                    // Prüft ob Vorgang leer ist 
                    if (order.Vorgang == emptyField)
                    {
                        order.Vorgang = "";
                    }

                    //Prüft ob Notiz leer ist
                    if (order.Notiz == emptyField)
                    {
                        order.Notiz = "";
                    }

                    //Prüft ob Dauer leer ist
                    if (order.Dauer == emptyField)
                    {
                        order.Dauer = "";
                    }


                    liste.Add(order);                                             
                }
            }               
        }

        catch (ArgumentException e)
        {

            Console.WriteLine("Fehlercode:" + e);
        }

    }
   // #endregion

    #region convertDateTime
    public DateTime convertDateTime(string date)
    {
        //konvertiert String zu Datetime
        DateTime newDate = DateTime.ParseExact(date,
                     "yyyyMMdd",
                      System.Globalization.CultureInfo.InvariantCulture);
        return newDate;

    }
    #endregion
}
}

When I load the CSV file every minute the amount of objects will increase extreamly. 当我每分钟加载CSV文件时,对象数量将急剧增加。 The Garbage Collector doesn't clear all old objects. 垃圾收集器不会清除所有旧对象。 can anybody help me to find this Problem? 有人可以帮助我找到这个问题吗?

my guess would be that your problem is that your using data tables where you don't need to. 我的猜测是您的问题是您不需要使用数据表。

A dataTable is a very complex item that is basically a code based database table and because of this is uses MarshalByValueComponent , which tells you that this can't be automatically GC'ed and as such requires you to call Dispose once you have finished using it. dataTable是一个非常复杂的项目,基本上是基于代码的数据库表,因此使用了MarshalByValueComponent ,它告诉您不能自动进行GC处理,因此需要在使用完之后调用Dispose。 。 (calling Dispose tells it to clean up its links to unmanaged code and be available to the garbage collector). (调用Dispose告诉它清除它到非托管代码的链接,并可供垃圾收集器使用)。

you have 2 options for triggering disposal a simple call to the Dispose function or a Using(){} statement 您有2个触发处置的选项,只需简单调用Dispose函数或Using(){}语句即可

you need to do this for all classes that are unmanaged (including StreamReader & FileStream) 您需要对所有非托管类(包括StreamReader和FileStream)执行此操作

as you aren't using the data table as a datatable, just a table then i would suggest removing it completely and just parsing your text file instead 因为您没有将数据表用作数据表,所以只建议使用一个表,则建议将其完全删除,然后解析您的文本文件

EDIT: 编辑:

Here as a quick and dirty model for a MVVM file parser 这是MVVM文件解析器的快速而肮脏的模型

XAML: XAML:

<Window x:Class="WpfApplication1.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:WpfApplication1"
        mc:Ignorable="d"
        Title="MainWindow" Height="350" Width="525">
    <Window.DataContext>
        <local:FileViewModel x:Name="vm" />
    </Window.DataContext>

    <DockPanel >
        <DockPanel DockPanel.Dock="Top">
            <Button DockPanel.Dock="Right" Click="Button_Click">Read</Button>
            <TextBox Text="{Binding File}" />
        </DockPanel>
        <ListView ItemsSource="{Binding ItemCollection}">
            <ListView.View>
                <GridView>
                    <GridViewColumn DisplayMemberBinding="{Binding field1}" Header="Feild1"/>
                    <GridViewColumn DisplayMemberBinding="{Binding field2}" Header="Field2"/>
                    <GridViewColumn DisplayMemberBinding="{Binding field3}" Header="Field3"/>
                    <GridViewColumn DisplayMemberBinding="{Binding field4}" Header="Field4"/>
                </GridView>
            </ListView.View>

        </ListView>
    </DockPanel>
</Window>

Code behind: 后面的代码:

public partial class MainWindow : Window
{
    public MainWindow()
    {
        this.InitializeComponent();
    }

    private void Button_Click(object sender, RoutedEventArgs e)
    {
        vm.ReadFile();
    }
}

File Reader 文件阅读器

public class FileViewModel : INotifyPropertyChanged
{
    private string _File;

    public string File
    {
        get { return _File; }
        set
        {
            _File = value;
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs("File"));
        }
    }

    public ObservableCollection<ItemModel> ItemCollection { get; } = new ObservableCollection<ItemModel>();

    public event PropertyChangedEventHandler PropertyChanged;

    public void ReadFile()
    {
        ItemCollection.Clear();

        using (StreamReader reader = new StreamReader(File))
        {
            var header =  reader.ReadLine();
            while(!reader.EndOfStream)
            {
                var data = reader.ReadLine();
                var item = ItemModel.Create(header, data, ',');
                ItemCollection.Add(item);
            }
        }
    }
}

Item Parser 项目解析器

public class ItemModel
{
    public static ItemModel Create(string colstr, string datastr, char delimiter)
    {
        var cols = colstr.Split(delimiter);
        var data = datastr.Split(delimiter);

        var item = new ItemModel();

        item.field1 = int.Parse(GetValue(cols, data, "field1"));
        item.field2 = DateTime.Parse(GetValue(cols, data, "field2"));
        item.field3 = GetValue(cols, data, "field3");
        item.field4 = double.Parse(GetValue(cols, data, "field4"));
        return item;
    }
    public static string GetValue(string[] cols, string[] data, string colName)
    {
        var colid = Array.IndexOf(cols, colName);
        if (colid == -1)
            return null;
        else
            return data[colid];
    }

    public int field1 { get; set; }
    public DateTime field2 { get; set; }
    public string field3 { get; set; }
    public double field4 { get; set; }

}

Demo File used 演示文件已使用

field2,field1,field4,field3
01-Jan-16,1,1.1,a
02-Jan-16,2,2.2,b
03-Jan-16,3,3.3,c
04-Jan-16,4,4.4,d

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 WPF为什么我的Line对象没有改变位置? - WPF Why are my Line objects not changing position? 为什么我的 wpf 应用程序在 web 浏览器中启动? - why is my wpf application starting in web browser? 为什么数据未绑定到我的 WPF 应用程序中的标签 - Why data is not bound to label in my WPF application 分析为什么在对应用程序进行性能分析时会在内存中保留更多的字符串对象 - Analyzing why more number of string objects are held up in the memory while profiling my application WPF / Winform应用程序中的内存占用量不断增加 - Memory footprint constantly increasing in WPF/Winform application 为什么我的WPF对话框出现在任务管理器-&gt;应用程序中? - Why does my WPF dialog appear in my task manager -> application? 为什么我的 WPF 应用程序字体在我的 PC 上看起来不同? - Why does my WPF application font look different on my PC? 为什么我的声音会在我的WPF应用程序中消失? - Why is my sound cutting out in my WPF application? 游戏在桌面上运行,但不在我的wpf应用程序中运行..为什么? - Game Running in desktop but not running in my wpf application..why? 为什么我的 WPF 应用程序没有释放其 memory? - Why doesn't my WPF application free up its memory?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM