Обработчик событий последовательного порта создает объект, который имеет значение NUll в основном коде

#c# #serial-port

#c# #последовательный порт

Вопрос:

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

Проблема в том, что когда файл закрыт, объект file кажется нулевым; Сам файл создается другим объектом, как и другие материалы, удаленные из моего примера кода.

По какой-то причине объект, созданный последовательным обработчиком событий, действителен, но файл внутри объекта имеет значение null.

Я очень опытный программист на C и linux, но новичок в C #, поэтому синтаксис и природа объекта все еще привлекают меня, но я не вижу причин, по которым это не должно работать, если я где-то не теряю контекст объекта. Это может быть проблемой, поскольку одновременно открыты четыре объекта последовательного порта для записи в четыре разных файла.

Я уже решил свою проблему с таймером, которая не работала бы при вызове из последовательного обработчика, перейдя из FOrms.timer в Timers.timer. поэтому мне интересно, является ли это проблемой с потоками.

Любой свет, который вы можете пролить, будет приветствоваться.

 class CommGroup
{
    private SerialPort _comPort;
    private System.Timers.Timer myTimer;
    private ResultsLog logFile = null;

    public CommGroup()
    {
        _comPort = new SerialPort(string name);
        _comPort.PortName = name;
        _comPort.DataReceived  = new SerialDataReceivedEventHandler(DataReceivedHandler);
        _comPort.Open();

         myTimer = new System.Timers.Timer();
         myTimer.Elapsed  = new System.Timers.ElapsedEventHandler(TimerEventProcessor);
    }

    private void TimerEventProcessor(Object myObject,
                                            EventArgs myEventArgs)
    {
        System.Timers.Timer timer = (System.Timers.Timer) myObject ;
        timer.Stop();

        if (logFile != null)
        {
            logFile.Close(); /* this fails due to null object */
        }
   }

    private void DataReceivedHandler(object sender,SerialDataReceivedEventArgs e)
    {
        SerialPort sp = (SerialPort)sender;
        if (myTimer.Enabled == false)
        {
            myTimer.Interval = 5000;
            myTimer.Start();
        }
        else
        {
            myTimer.Stop();
            myTimer.Interval = 5000;
            myTimer.Start();
        }

        if (logFile == null)
        {
            logFile = new ResultsLog("Filename");
        }
        logFile.LogResult(sp.ReadExisting());
    }
}

public class ResultsLog
{
    private StreamWriter resultFile;

    public ResultsLog(string filename)
    {
            StreamWriter resultFile = new StreamWriter(filename, true);
    }

    public void Close(string errorname)
    {
        if (this.resultFile != null)
        {
            resultFile.Flush();
            resultFile.Close();
        }
        else
        {
            MessageBox.Show("File NULL Error "   errorname, "File Close");
        }
    }

    public void LogResult(string result)
    {
        if (resultFile != null)
        {
            resultFile.Write(result);
        }
    }
}
  

Ответ №1:

Является ли ваш результирующий файл проблемным null?

Вы повторно объявляете локально в своем конструкторе ResultsLog. Должно быть:

 public ResultsLog(string filename)
{
        resultFile = new StreamWriter(filename, true);
}
  

Ответ №2:

Определенно может быть потоковая передача, потому что у вас есть несколько потоков, обращающихся к объекту журнала без синхронизации.

Используйте блокировку вокруг ваших доступов к переменной и посмотрите, поможет ли это.