2015-01-25 3 views
1

DB를 60 초마다 확인하는 간단한 응용 프로그램을 개발하고 있습니다. 나는 그것을하기 위해 System.Threading.TimerCallback을 사용한다. 그러나 내가 앱을 돌릴 때, 그것은 한 번만 틱한다. 나는 그것이 작동하지만, m 그냥 한 번 실행 d를 호출 할 때System.Threading.TimerCallback은 Entity Framework를 사용할 때 한 번만 발생합니다.

private void Form1_Load(object sender, EventArgs e) 
    { 
     // Create the delegate for the Timer type. 
     System.Threading.TimerCallback timeCB = new System.Threading.TimerCallback(d); 

     // Establish timer settings. 
     System.Threading.Timer t = new System.Threading.Timer(
      timeCB,  // The TimerCallback delegate object. 
      null,  // Any info to pass into the called method (null for no info). 
      0,   // Amount of time to wait before starting (in milliseconds). 
      1000);  // Interval of time between calls (in milliseconds). 
    } 

    void m(object o) 
    { 
     System.Media.SystemSounds.Hand.Play(); 
     SReminderEntities ctx = new SReminderEntities(); 

     var jobs = (from m in ctx.Messages 
        select m).ToList(); 

     var seljobs = from j in jobs 
         where j.RemindeTime.Date == DateTime.Now.Date 
          && j.RemindeTime.Hour == DateTime.Now.Hour 
          && j.RemindeTime.Minute == DateTime.Now.Minute 
         select j; 

     foreach (var j in seljobs) 
     { 
      // SendGmail("iReminder", j.Text, new string[] { j.User.Email }, "[email protected]"); 
      //this.sendSMS(j.User.Mobile, j.Text); 
      System.Media.SystemSounds.Hand.Play(); 
     }//foreach 
    } 

    void d(object o) 
    { 
     MessageBox.Show("Test"); 
    } 

: 여기

는 코드입니다. 문제점은 무엇이며 어떻게 해결할 수 있습니까? 고맙습니다.

+0

타이머를 제외한 모든 코드를 삭제하십시오. 틱 핸들러에 MessageBox를 추가합니다. 그것은 여전히 ​​한 번만 발사됩니까? – usr

답변

3

System.Threading.Timer 클래스는 자신 만의 참조를 유지해야합니다. 인스턴스에 도달 할 수있게하는 루트 데이터 구조 자체가 없습니다. 따라서 참조를 직접 보관하지 않으면 가비지 수집기가 개체를 회수하여 타이머를 삭제합니다.

양식 클래스에 개인 인스턴스 필드를 만들고 대신 참조를 저장하십시오.

부분적으로 읽는, 또한 the documentation 참조 :

을만큼 당신이 타이머를 사용하고, 당신은에 대한 참조를 유지해야합니다. 모든 관리 대상 개체와 마찬가지로 Timer는 참조가 없을 때 가비지 수집 대상이됩니다. Timer가 여전히 활성화되어 있어도 타이머가 수집되지 않습니다.

관련 문제