Bilmek istediğin her şeye ulaş

Bir programın yaptığı işlemleri daha sonra devam etmek şartı ile durdurup sonra devam ettirmek istersek, bununla ilgili program mantığını nasıl düşünmek ve uygulamak gerekir?

c# dilinde windows uygulaması, database ile sürekli bir iletişim halinde ve arada web den bilgi indiren tamamen otomatik işleyen bir yapıdan bahsediyorum. mesela elektrik kesildi ve ben programı durdurmak istiyorum sonra da kaldığı yerden devam etmesini istediğimde devam tuşuna basmam yeterli olsun mesela.Düzenle
Bu genel bir sorun, onun için standardlaşmış bir çözümü var: Serilization. msdn.microsoft.com/en-us/library/ms2338... buradan her türlü bilgiye erişebilirsin. Mantık object-oriented bir sistemde her nesneyi veya nesne grubunu ham-data'ya dolayısıyla dosyaya çevirebilirsin. Program açıldığında try içinde deserialize yap. Başarısızsa (catch içinde) baştan başla ve nesneleri çıkar. Başarılı olursa, dosyadan gelen nesneleri kullan (ki bu kaldığın yerden devam etmek demek) .

Ben bu tekniği uzun zamandır kullanıyorum. Çok iyi çalışıyor.

Not: Dosya türü olarak xml'i tavsiye ederim. Program dışında da dosya okunup anlaşılabiliyor.
  • Paylaş
1

Unluckypod, teşekkür ederim.

Bunun için size iki faktör öneriyorum:
  1. Bu tür uygulamalar için bellekte veya kalıcı bir yerde (diskte, veritabanında, regeditte) uygulamanın son işlediği veriyi tutmak ve sonrasında uygulama yeniden işlemlerine başladığında kaydedilen değeri okuyarak, programın nereden ve nasıl çalışmaya başlayacağına karar vermesi sağlanabilir.
  2. Programın kapatılıp açılması durumuna ilave olarak, program henüz çalışıyor iken durdurulup tekrar başlatılması durumu için ise bir bayrak tutabilir ve bu bayrağı okuyarak çalışıp çalışmayacağınıza karar verebilirsiniz.


Programınızın nasıl bir işleyişi ve görevi olduğunu bilmiyorum, fakat yukarıda bahsettiklerimi anlamanız için örnek bir sınıf yazdım.

 public class Back
 {
 //<a href='http://www.inploid.com/t/bir-programin-yaptigi-islemleri-daha-sonra-devam-etmek-sarti-ile-durdurup-sonra-devam-ettirmek-istersek-bununla-ilgili-program-mantigini-nasil-dusunmek-ve-uygulamak-gerekir/59238/' target='_blank' title='inploid.com/t/bir-programin-yaptigi-islemleri-daha-sonra-devam-etmek-sarti-ile-durdurup-sonra-devam-ettirmek-istersek-bununla-ilgili-program-mantigini-nasil-dusunmek-ve-uygulamak-gerekir/59238/'>inploid.com/t/bir-programin-yaptigi-isle... </a>
 
 /*
 * Veritabanından bir Id değeri ile 1000'lik bloklar halinde kayıt alan bir programınızın olduğunu varsayarak sorunuza verdiğim cevabı aşağıda implemente ettim.
 */
 
 /// <summary>
 /// Bahsettiğim bayrak.
 /// İlgili otomatik işlemin durumunu tutmak üzere kullandığınız değerleri içeriyor.
 /// </summary>
 public enum ComponentStatus
 {
 Unknown = 0,
 Running = 1,
 Paused = 2,
 Stopped = 3,
 Failed = 4
 }
 
 /// <summary>
 /// Otomatik işleminizi yapan bileşenin şu anki durumu
 /// </summary>
 public ComponentStatus CurrentState { get; private set; }
 
 /// <summary>
 /// Program ne zaman kapanırsa kapansın, yaptığı işlem için kullandığı değeri kalıcı olarak tutar iseniz bu şekilde kullanabilirsiniz.
 /// </summary>
 public int LastRecordId { get; private set; }
 
 /// <summary>
 /// Programınızın ilk açılışta çalıştırılan metodu.
 /// </summary>
 public void Initialize()
 {
 //Burada programın işlemini devam ettirmesi için gereken son duruma ait değeri yükleyin.
 //Bu örnekte ilgili değer, LastRecordId oluyor.
 //Örneğin regedit'e son işlemde kullandığınız LastRecordId'i yazdığınızı varsayalım.
 //Öyleyse burada, regedit'ten ilgili değeri okuyup LastRecordId'ye atayın.
 }
 
 
 /// <summary>
 /// OnInitialize'den sonra çalışan metot
 /// </summary>
 public void OnStart()
 {
 //Gerekli son durumlar ile programınız yüklendi ve oto işlemleri burada başlatacaksınız.
 if (this.CurrentState == ComponentStatus.Running) //Bir kez çalıştıktan sonra tekrar bu metodun çalışıp tekrar işlemleri başlatmasını engelle
 return; //Zaten çalışıyor.
 
 Thread autoProccessThread = new Thread(this.Do);
 autoProccessThread.Start(); //Otomatik olarak yürüteceğiniz işlemi ayrı bir Thread içerisinde arka planda başlattınız.
 this.CurrentState = ComponentStatus.Running; //Dolayısıyla bileşenin şu anki durumunu çalışıyor olarak değiştirmelisiniz.
 }
 
 
 /// <summary>
 /// Otomatik olarak işlemlerinizi yaptığınız metot.
 /// </summary>
 public void Do()
 {
 while (CurrentState == ComponentStatus.Running) //Bileşen Running durumunda olduğu sürece işlemleri yapmaya devam et.
 {
 try
 {
 /*
 * OnInitalize metodunda son Id değerini yüklediğimiz için, 
 * eğer program az önce kırıldı ve şu an tekrar çalıştırıldıysa 
 * bile problem olmaksızın kaldığı yerden işlemlerine devam edebilecek
 */
 
 this.LastRecordId = this.GetLastRecordOnDb(this.LastRecordId); //Veritabanında yürüttüğünüz otomatik işlemin bu olduğunu varsayalım.
 
 }
 catch (Exception ex)
 {
 //Programı tekrar çalışamayacak duruma getiren kritik bir hata geldi ise
 CurrentState = ComponentStatus.Failed; //Durum değişti, döngüden çıkılır. Gerekli loglamalar yapılır.
 }
 
 Thread.Sleep(100); //Her turda belli bir bekleme iyi olacaktır.
 }
 }
 
 /// <summary>
 /// Parametredeki Id değerinden itibaren veritabanından 1000 lik bloklar halinde kayıtları getiren bir oto metodunuz olduğunu varsayıyorum.
 /// Geriye döndürdüğü değer, bir sonraki veri bloğunun hangi Id ile başladığını belirtir.
 /// </summary>
 /// <param name="recordId"></param>
 /// <returns></returns>
 private int GetLastRecordOnDb(int recordId)
 {
 int rvnextRecId = recordId;
 //Bir takım işlemler ve sıradaki veriyi çekmek için gereken Id değerini rvnextRecId değişkenine atadınız.
 return rvnextRecId;
 }
 
 /// <summary>
 /// Programın kapatılma anında tetiklenen bir metot olduğunu varsayın
 /// </summary>
 public void OnClose()
 {
 //Diğer kapatma işlemleri... ... 
 //Programın durumunu değiştir.
 this.CurrentState = ComponentStatus.Stopped; //Ayrı bir thread içerisinde oto işlemimiz sürerken, bileşen durumu bu noktada değiştiği için, ilgili arka plan işlemi (yani Do metodu) çalışmayı bitirecek.
 //this.LastRecordId değerini Regedite kaydet.
 }
 
 }
  • Paylaş
12

Unluckypod, ayrıntılı cevap için teşekkür ederim. peki başından sonuna kadar çoklu kanal ile çalışıyorsa, nasıl bir yaklaşım benimsemeliyim genel olarak?

Brutal Code, Başından sonuna kadar derken nasıl bir durumdan bahsettiğinizi anlamadım. Biraz daha detaylandırabilir misiniz?

Kullandığınız yapı nedir, win form, win service? Yukarıda bahsini ettiğim durum için önerim win service kullanmanızdır.

Unluckypod, win form. dielim winform açıldığında kullanıcı bazı girdiler girdikten sonra başlat butonuna basınca aynı akışı kullanan thread ler olacak. bütün threadler işini bitirince de işlem tamamlandı bilgisi verilecek kullanıcıya.

Brutal Code, Win form'da kullanıcı ile etkileşimde olan arayüzün thread'i main thread'dir ve siz uzun süreli bir işlem yapacaksanız işlem esnasında arayüzün donmaması için, işlemi ayrı bir thread'e vererek yaptırmanız gereklidir.

Fakat bu durumda da işlem bittiğinde arayüze bir mesaj göndermek kısmında bir istisna çıkıyor. Şöyle ki, ayrı bir thread içerisinde işlem yaptığınızdan dolayı, arayüze ait bir kontrole, örneğin label, erişip değerini değiştirmeniz demek, başka bir thread'den main thread'e erişmeniz demektir ve bu hata almanıza sebep verir.

Bu hatayı aşmak için ise invoke required mevzularına bakmanızı öneririm.

Thread yerine, Paralel veya Task kullanırsanız, işlem bittiğinde hangi metodun tetikleneceğini de belirtebilirsiniz.

Unluckypod, yukarıda yazdığınız mevzuya tekrar odaklanmak için bi bakıyım dedim, tekrar inceledim de da bu yazdıklarınızın hakkını yeterince vermemişim:)) internette sabaha kadar arasam bulamazdım:)) tekrar eyvallah:)

Brutal Code, Rica ederim :) Probleminizi çözmek için uygulamayı deneyip sonuç alabildiniz mi? Kolay gelsin.

Unluckypod, problemi şimdilik sabunladım dielim öğrenci diliyle, iş görüyor. ama yönteminizi kesinlikle uygulayacam pek tabii, sadece henüz zamanı gelmedi. yani sonuçta henüz öğrenme aşamasındayım ve vakit ayırmaya çalışıyorum hem mvc ye hem de c# jquery vs.. meselelerine. bi de kapsamlı uydurma bir proje ile öğrendiklerimi pekiştirmeye çalışıyorum. projede sizin önerdiğiniz yöntemi kullanarak da kapanışı yapmak istiyorum. o zaman tam kapsamlı bir proje olacak ama uzun sürecek gibi çünkü aynı anda mvc yi bitirdikten sonra bi de biraz kapsamlı bir site yapmak istiyorum ki ikisi birlikte epey zamanımı alacaktır. Maksat tam anlamıyla bişileri öğrenmek. Bakalım zaman neler gösterecek:)

Unluckypod, yani mesela mvc de html.renderaction bölümü hata veriyor 3 gündür çözüm bulamadım bit kadar soruna:)

Brutal Code, Merak etmeyin, heves edip peşinden bu şekilde koştuğunuzda zaman iyi şeyler gösterecektir.
Mvc ile ilgili probleminizi de buraya yazmadıysanız yazmanızı tavsiye ederim.
Kolay gelsin.

Unluckypod, teşekkür ederim gerçekten...mvc sorusunu aslında buraya da yazdım ama detaylı yazamadım. detaylı olarak donanımforum a yazdım ama ordan bişi çıkmadı. linki de şu ; forum.donanimhaber.com/m_94875240/f_//tm...

Brutal Code, Donanım haberde bu tür sorular için cevap verebilecek katılımcılar var mı bilmiyorum, ama stackoverflow'da daha kolay çözüm bulabileceğini düşünüyorum.

Unluckypod, evet ben de aynı fikirdeyim. olmadı orayı deniyim en iyisi.

Bu yazılımcı kafası başka birşey diyomda inanmıyorlar bana. : -) hayır, çalışan şeyi elleme diye söz vardır, bırak çalışsın işte.
Ama yok yazılımcı kafası illa bi bakacak "böyle böyle olursa şöyle şöyle olurmu ya la" diyerek. Dost tavsiyesi çalışan şeyi elleme : -)
  • Paylaş
2
Sonraki Soru
HESAP OLUŞTUR

İstatistikler

440 Görüntülenme4 Takipçi3 Yanıt