c# - System.Threading.Timer 不触发我的 TimerCallBack 委托(delegate)

标签 c# windows-services timer

我正在使用 C# 编写我的第一个 Windows 服务,我在使用 Timer 类时遇到了一些问题。

当服务启动时,它按预期运行但代码不会再次执行(我希望它每分钟运行一次)

请快速查看附加的源代码,如果您发现任何明显的错误,请告诉我!

TIA

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Linq;
using System.ServiceProcess;
using System.Text;
using System.Threading;
using System.IO;

namespace CXO001
{
    public partial class Service1 : ServiceBase
    {
        public Service1()
        {
            InitializeComponent();
        }

         /*
         * Aim: To calculate and update the Occupancy values for the different Sites
         * 
         * Method: Retrieve data every minute, updating a public value which can be polled
         */

        protected override void OnStart(string[] args)
        {
            Daemon();
        }

        public void Daemon()
        {
            TimerCallback tcb = new TimerCallback(On_Tick);
            TimeSpan duetime = new TimeSpan(0, 0, 1);
            TimeSpan interval = new TimeSpan(0, 1, 0);
            Timer querytimer = new Timer(tcb, null, duetime, interval);
        }

        protected override void OnStop()
        {

        }



        static int[] floorplanids = new int[] { 115, 114, 107, 108 };
        public static List<Record> Records = new List<Record>();
        static bool firstrun = true;

        public static void On_Tick(object timercallback)
        {
            //Update occupancy data for the last minute
            //Save a copy of the public values to HDD with a timestamp

            string starttime;

            if (Records.Count > 0)
            {
                starttime = Records.Last().TS;
                firstrun = false;
            }
            else
            {
                starttime = DateTime.Today.AddHours(7).ToString();
                firstrun = true;
            }

            DateTime endtime = DateTime.Now;
            GetData(starttime, endtime);
        }

        public static void GetData(string starttime, DateTime endtime)
        {
            string connstr = "Data Source = 192.168.1.123; Initial Catalog = Brickstream_OPS; User Id = Brickstream; Password = bstas;";
            DataSet resultds = new DataSet();

            //Get the occupancy for each Zone
            foreach (int zone in floorplanids)
            {
                SQL s = new SQL();
                string querystr = "SELECT SUM(DIRECTIONAL_METRIC.NUM_TO_ENTER - DIRECTIONAL_METRIC.NUM_TO_EXIT) AS 'Occupancy' FROM REPORT_OBJECT INNER JOIN REPORT_OBJ_METRIC ON REPORT_OBJECT.REPORT_OBJ_ID = REPORT_OBJ_METRIC.REPORT_OBJECT_ID INNER JOIN DIRECTIONAL_METRIC ON REPORT_OBJ_METRIC.REP_OBJ_METRIC_ID = DIRECTIONAL_METRIC.REP_OBJ_METRIC_ID WHERE (REPORT_OBJ_METRIC.M_START_TIME BETWEEN '" + starttime + "' AND '" + endtime.ToString() + "') AND (REPORT_OBJECT.FLOORPLAN_ID = '" + zone + "');";
                resultds = s.Go(querystr, connstr, zone.ToString(), resultds);
            }

            List<Record> result = new List<Record>();
            int c = 0;

            foreach (DataTable dt in resultds.Tables)
            {
                Record r = new Record();
                r.TS = DateTime.Now.ToString();
                r.Zone = dt.TableName;
                if (!firstrun)
                {
                    r.Occupancy = (dt.Rows[0].Field<int>("Occupancy")) + (Records[c].Occupancy);
                }
                else
                {
                    r.Occupancy = dt.Rows[0].Field<int>("Occupancy");
                }
                result.Add(r);
                c++;
            }

            Records = result;
            MrWriter();
        }

        public static void MrWriter()
        {
            StringBuilder output = new StringBuilder("Time,Zone,Occupancy\n");

            foreach (Record r in Records)
            {
                output.Append(r.TS);
                output.Append(",");
                output.Append(r.Zone);
                output.Append(",");
                output.Append(r.Occupancy.ToString());
                output.Append("\n");
            }

            output.Append(firstrun.ToString());
            output.Append(DateTime.Now.ToFileTime());

            string filePath = @"C:\temp\CXO.csv";
            File.WriteAllText(filePath, output.ToString());
        }

    }
}

最佳答案

manual states :

As long as you are using a Timer, you must keep a reference to it. As with any managed object, a Timer is subject to garbage collection when there are no references to it. The fact that a Timer is still active does not prevent it from being collected.

您的计时器可能正在被 GC 收集。

关于c# - System.Threading.Timer 不触发我的 TimerCallBack 委托(delegate),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4711808/

相关文章:

c# - 将 SqlCommand 与 C# 变量一起使用

service - Windows服务 "Starting"

java - 试图将代码 move 到 main - Java

c# - 由于缓存委托(delegate),C#编译器的行为异常

c# + WebForms + 静态——最佳实践是什么?

c# - 在 C# 中查找给定日期的最接近月末

c# - 启动 WCF 客户端时为 "No default endpoint found"

windows-services - 在 Windows 服务中运行 cdb 时无法下载 Microsoft 符号

java - 如何在Android中正确实现定时器?

C# - 如何在一段时间内阻止方法返回?