Ссылочная DLL в ссылочном .NET C # проекте не освобождает память при закрытой форме - PullRequest
2 голосов
/ 10 января 2012

Я использую демонстрационную версию SDK (просто скомпилированный dll), чтобы веб-камера считывала штрих-коды в приложении Windows.

Я не могу заставить ее освободить память, когда я закончу сформа.Пока форма открыта, она будет продолжать использовать больше памяти, пока не будет закрыта.Он не освободит память при закрытии.Когда я снова открываю ту же форму, она начинает сжимать больше памяти, пока не закроется.Этот процесс продолжается до тех пор, пока не останется свободной памяти, а затем основное приложение не будет работать.

Очевидно, что проблема в том, что barcode.dll не освобождает ресурсы.Однако, разве я не смогу убить свой проект, на который ссылаются, и этот оскорбительный dll, чтобы заставить его освободить память, которая не откажется?

Я пытался:

  1. Вызов gc.Collect напрямую
  2. Удаление всех событий при закрытии формы
  3. Утилизация вручную таймеров и штрихкодов сканирования объектов

Может кто-нибудь сказать мне, что я делаю неправильноили дать мне какие-нибудь идеи?Я надеюсь, что я разместил достаточно информации.

Вот код:

originalForm.vb (в основном проекте)

Dim frm As New Library.Helpers.frmWebcamScanner(True)
If (frm.ShowDialog() = Windows.Forms.DialogResult.OK) Then txtVIN.Text = frm.BarcodeReading
frm.Dispose()

Затем я добавил это после строки frm.Dispose ():

GC.Collect()
GC.WaitForPendingFinalizers()
GC.Collect()

secondForm.cs (в указанном проекте)

namespace Library.Helpers
{
public partial class frmWebcamScanner : Form
{
    private bool _ScanningForVIN = false;

    /// <summary>
    /// The results of the scan
    /// </summary>
    public string BarcodeReading = "";

    /// <summary>
    /// 
    /// </summary>
    /// <param name="ScanningForVIN">Are you trying to read a VIN? t/f</param>
    public frmWebcamScanner(bool ScanningForVIN)
    {
        _ScanningForVIN = ScanningForVIN;
        InitializeComponent();
    }

    private void frmWebcamScanner_Load(object sender, EventArgs e)
    {
        this.Top = this.Top + 10;
        barcodeReader1.Start();
        timer1.Start();
    }

    private void barcodeReader1_BarcodeReady(object sender, BarcodeEvent e)
    {
        BarcodeReading = e.barcode.barcode;
        if (_ScanningForVIN)
        {
            //Remove the leading *I if there:
            BarcodeReading = BarcodeReading.Replace("*I", "");
            //Remove all asterisks:
            BarcodeReading = BarcodeReading.Replace("*", "");
        }
        this.DialogResult = System.Windows.Forms.DialogResult.OK;
        PrepAndClose();
    }

    private void frmWebcamScanner_KeyDown(object sender, KeyEventArgs e)
    {
        if (e.KeyCode == Keys.Escape)
        {
            this.DialogResult = System.Windows.Forms.DialogResult.Cancel;
            PrepAndClose();
        }
    }

    private void timer1_Tick(object sender, EventArgs e)
    {
        this.DialogResult = System.Windows.Forms.DialogResult.Abort;
        PrepAndClose();
    }

    private void PrepAndClose()
    {
        timer1.Stop();
        barcodeReader1.Stop();
        this.Close();
    }       
}
}

Затем я настроил код файла designer.cs, пытаясь освободить все, чтобы запустить сборщик мусора. Я установил точку останова ввот и проверил все прошло нормально.

из файла designer.cs:

/// <summary>
/// Clean up any resources being used.
/// </summary>
/// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param>
protected override void Dispose(bool disposing)
{
    if (disposing && (components != null))
    {

        barcodeReader1.Stop();
        timer1.Stop();

        this.Load -= this.frmWebcamScanner_Load;
        this.KeyDown -= this.frmWebcamScanner_KeyDown;
        this.barcodeReader1.BarcodeReady -= this.barcodeReader1_BarcodeReady;
        this.timer1.Tick -= this.timer1_Tick;

        barcodeReader1.Dispose();
        barcodeReader1 = null;

        components.Dispose();
    }
    base.Dispose(disposing);
}
...