dosya meşgul hatası

Delphi'de kod yazma ile ilgili sorularınızı bu foruma yazabilirsiniz.
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

dosya meşgul hatası

Mesaj gönderen duraumsa »

Kolay gelsin üstatlar.
iki adet proses yazdım biri bitmap oluşturup kapatıyor diğeri bu bitmap alıp okuyup kapatıyor.
bir günlük çalışmada yaklaşık 10 defa çakışıyor. Dosya meşgul hatası veriyor bunu engellemenin bir yolu varmıdır. dosya meşgul ise diğer prosese bekle diyeceğim.

Şimdiden teşekkürler
ertank
Kıdemli Üye
Mesajlar: 1648
Kayıt: 12 Eyl 2015 12:45

Re: dosya meşgul hatası

Mesaj gönderen ertank »

Merhaba,

Kullandığınız Delphi sürümü nedir?
Bitmap oluşturan proses dosyaya nasıl yazıyor?
Bitmap okuyan proses dosyadan nasıl okuyor?

Kod paylaşabilir iseniz yardımcı olmak mümkün olabilir.
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

Re: dosya meşgul hatası

Mesaj gönderen duraumsa »

bitmap oluşturan proses kodu:

Kod: Tümünü seç

procedure TForm1.Button3Click(Sender: TObject);

var
  it,jt : integer;
  bmp: TBitMap;
  r : Trect;
begin
   try
   bmp := TBitmap.Create;
     //  bmp.Width := Image5.Width;
     //  bmp.Height := Image5.Height;
       bmp.Width := 1000;
       bmp.Height := 210;

       bmp.PixelFormat := pf24bit;
       r := Rect(0, 0, bmp.Width, bmp.Height);
       bmp.Canvas.StretchDraw(r, Image1.Picture.Graphic);
       bmp.SaveToFile('C:\silim_setup\resim13.bmp');
       image2.Picture.LoadFromFile('C:\silim_setup\resim13.bmp');
   finally

   end;

   bmp.Free;
end;
bitmap okuyan proses kodu

Kod: Tümünü seç

procedure TForm4.Button17Click(Sender: TObject);

var
  it,jt : integer;
  bmp,resimilk, resimson : TBitMap;
  r : Trect;
begin
try
    bmp := TBitmap.Create;
 //  bmp.Width := Image5.Width;
 //  bmp.Height := Image5.Height;
   bmp.Width := 1000;
   bmp.Height := 210;

   bmp.PixelFormat := pf24bit;
  // r := Rect(0, 0, bmp.Width, bmp.Height);
  // bmp.Canvas.StretchDraw(r, Image5.Picture.Graphic);
  // bmp.SaveToFile('C:\silim_setup\resim13.bmp');
   image2.Picture.LoadFromFile('C:\silim_setup\resim13.bmp');
finally

end;
   bmp.Free;
 end;
 
ertank
Kıdemli Üye
Mesajlar: 1648
Kayıt: 12 Eyl 2015 12:45

Re: dosya meşgul hatası

Mesaj gönderen ertank »

Merhaba,

Kullanıcı çok uğraşsa dahi buton tıklamasını o kadar hızlı yapıp bitmap dosya yazma işlemi bitmeden okuma butonunu tıklayamaz diye düşünüyorum.

Ancak, işletim sistemi birçok dosya işlemini "cache" kullanarak yaptığı için yazılan dosya diske gerçekten yazılması anında değil gecikmeli olabilir.

Aşağıdaki kod dosyanın kullanılabilir olduğunu kontrol edip işlemin devam etmesini sağlıyor. Eğer sorun yukarıdaki gibi "cache" kaynaklı ise sorunu çözmesi gerekir.

Kod: Tümünü seç

uses
  DateUtils;


function WaitForFileReady(const FileName: string; const Timeout: Cardinal): Boolean;
var
  FileHandle: THandle;
  StartTime: TDateTime;
begin
  StartTime := Now();

  while (MilliSecondsBetween(Now, StartTime) < Timeout) or (Timeout = 0) do
  begin
    FileHandle := CreateFile(PChar(FileName), GENERIC_READ, 0, nil, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, 0);

    if (FileHandle <> INVALID_HANDLE_VALUE) then
    begin
      CloseHandle(FileHandle);
      Exit(True);
    end;

    Sleep(50);
  end;

  Exit(False);
end;


procedure TForm2.Button1Click(Sender: TObject);
var
  Bmp: TBitMap;
begin
  Bmp := TBitmap.Create;
  try
    Bmp.Width := 1000;
    Bmp.Height := 210;
    Bmp.PixelFormat := pf24bit;

    // Maksimum 1 saniye dosyanın kullanılabilir olmasını bekle.
    // Eğer dosya o anda kullanılabilir ise işlem hemen devam eder.
    // İhtiyaca göre süre uzatılabilir.
    if WaitForFileReady('C:\silim_setup\resim13.bmp', 1000) then
    begin
      Image2.Picture.LoadFromFile('C:\silim_setup\resim13.bmp');
    end
    else
    begin
      ShowMesage('Dosya yok veya kullanılabilir değil!');
    end;
  finally
    bmp.Free();
  end;
end;
Paylaştığınız kod ile ilgili olarak. Nesneleri create edip hafıza kaçağına sebep olmamak için free etme kodunuz oldukça hatalı.
Bir nesneyi aşağıdaki şekilde create etmemelisiniz.

Kod: Tümünü seç

try
    bmp := TBitmap.Create;
Eğer nesne create edilemez ise sizin kodunuz free etmeye çalışır ve bu access violation hatasına sebep olur (oluşturulmamış bir nesne free edilemez). Doğrusu şöyle olmalı:

Kod: Tümünü seç

bmp := TBitmap.Create;
try
Bunun dışında aşağıdaki kodunuz da hatalı:

Kod: Tümünü seç

finally

end;
   bmp.Free;
Burada try..finally bloğu dışında bmp nesnesini free etmişsiniz. Eğer try ile finally arasındaki kod bir hata oluşturur ise bmp nesnesi free edilmeyip hafıza kaçağı oluşacaktır. Doğrusu şöyle olmalı:

Kod: Tümünü seç

finally
  bmp.Free();
end;
Bazı durumlarda aynı prosedür/fonksiyon içinde birden fazla nesne oluşturup hafıza kaçağı kontrolü yapılması gerekir. Nesne sayısı arttıkça try..finally blok sayısı da artacağı ve kod okunabilirliğini etkileyeceği gibi olumsuzlukların önüne geçmek ve aynı zamanda hafıza kaçağına sebep olmamak için aşağıdaki gibi bir kullanım tercih edilebilir:

Kod: Tümünü seç

var
  Bitmap1: TBitmap;
  Bitmap2: TBitmap;
  Bitmap3: TBitmap;
begin
  Bitmap1 := nil;
  Bitmap2 := nil;
  Bitmap3 := nil;
  try
    Bitmap1 := TBitmap.Create();
    Bitmap2 := TBitmap.Create();
    Bitmap3 := TBitmap.Create();
    // burada normal şekilde işlemler yapılabilir.
  finally
    Bitmap1.Free();
    Bitmap2.Free();
    Bitmap3.Free();
  end;
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

Re: dosya meşgul hatası

Mesaj gönderen duraumsa »

Cevabınız için teşekkür ederim.

Aynı program içinde iki farklı buton değil hocam. İki farklı programdaki butonlar. programın biri haberleşme ile verileri çekip resmi oluşturuyor diğeri bu resmi okuyor.

Kod yazmadaki hatalarım için verdiğiniz tavsiyeler içinde teşekkür ederim hocam
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

Re: dosya meşgul hatası

Mesaj gönderen duraumsa »

Kolay gelsin Üstad

vermiş olduğunuz fonksiyonun her iki projemede uyguladım.

Denedim olmadı

Cannot open file "C:\silim_setup\resim13.bmp".
The process cannot access the because it is begin used by another process.


bu hata arada devam ediyor. başka yöntem varmıdır acaba
ertank
Kıdemli Üye
Mesajlar: 1648
Kayıt: 12 Eyl 2015 12:45

Re: dosya meşgul hatası

Mesaj gönderen ertank »

duraumsa yazdı: 18 Eki 2019 09:28 vermiş olduğunuz fonksiyonun her iki projemede uyguladım.
Kodunuzun son halini paylaşabilir misiniz?
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

Re: dosya meşgul hatası

Mesaj gönderen duraumsa »

resmi oluşturan kod

Kod: Tümünü seç

procedure TForm1.Button3Click(Sender: TObject);
  var
    bmp: TBitMap;
    r : Trect;
  begin
  bmp := TBitmap.Create;
     try
         bmp.Width := 1000;
         bmp.Height := 210;
         bmp.PixelFormat := pf24bit;


            if WaitForFileReady('C:\silim_setup\resim13.bmp', 1000) then
            begin
            r := Rect(0, 0, bmp.Width, bmp.Height);
            bmp.Canvas.StretchDraw(r, Image1.Picture.Graphic);
            bmp.SaveToFile('C:\silim_setup\resim13.bmp');
            image2.Picture.LoadFromFile('C:\silim_setup\resim13.bmp');
            end
            else
            begin
              ShowMessage('Dosya okuma hatası !!!');
            end;
     finally
         bmp.Free;
     end;


  end;
resmi okuyan kod

Kod: Tümünü seç

procedure TForm4.Button17Click(Sender: TObject);

var
  it,jt : integer;
  bmp,resimilk, resimson : TBitMap;
  r : Trect;
  begin
    bmp := TBitmap.Create;
      try

      bmp.Width := 1000;
      bmp.Height := 210;
      bmp.PixelFormat := pf24bit;
            if WaitForFileReady('C:\silim_setup\resim13.bmp', 1000) then
            begin
              Image2.Picture.LoadFromFile('C:\silim_setup\resim13.bmp');
            end
            else
            begin
              ShowMessage('Dosya okuma hatası !!!');
            end;

      finally
      bmp.Free;
      end;

 end;
ertank
Kıdemli Üye
Mesajlar: 1648
Kayıt: 12 Eyl 2015 12:45

Re: dosya meşgul hatası

Mesaj gönderen ertank »

Merhaba,

Dosya okuma kodunuzu aşağıdaki hale getirdiğiniz zaman aldığınız hata mesajını görüntü olarak paylaşabilir misiniz?

Kod: Tümünü seç

var
  it, jt: integer;
  bmp, resimilk, resimson: TBitMap;
  r: Trect;
begin
  bmp := TBitMap.Create;
  try
    bmp.Width := 1000;
    bmp.Height := 210;
    bmp.PixelFormat := pf24bit;
    if WaitForFileReady('C:\silim_setup\resim13.bmp', 1000) then
    begin
      try
        Image2.Picture.LoadFromFile('C:\silim_setup\resim13.bmp');
      except
        on E: Exception do
        begin
          ShowMessage('HATA: Dosya okunamadı: C:\silim_setup\resim13.bmp' + sLineBreak +
            'Orjinal Hata: ' + E.Message);
        end;
      end;
    end
    else
    begin
      ShowMessage('Dosya okuma hatası !!!');
    end;
  finally
    bmp.Free;
  end;
end;
Kullanıcı avatarı
loaded
Üye
Mesajlar: 122
Kayıt: 12 Eki 2010 09:45
Konum: Konya
İletişim:

Re: dosya meşgul hatası

Mesaj gönderen loaded »

Benim bu tür asenkron durumlar için kullandığım basit bir yöntem denemekte fayda var

Kod: Tümünü seç

procedure TForm1.Button1Click(Sender: TObject);
var
  err:Boolean=false;
begin
  repeat
    try
    // Yazma Okuma Fonksiyonu
    image1.Picture.Bitmap.SaveToFile('C:\deneme.png');
    // Yazma Okuma Fonksiyonu Sonu
    err:=false;
    caption:=timetostr(time) + ' Zamanında Yazıldı / Okundu ' ;
    except
    err:=true;
    caption:= ' Hata Oluştu ' ;
    end;
    Application.ProcessMessages;
  until not err;
end;
Kalk ve işe yarar bir şey yap! Çünkü Allah (c.c.) yeniden başlayanların yardımcısıdır.
ertank
Kıdemli Üye
Mesajlar: 1648
Kayıt: 12 Eyl 2015 12:45

Re: dosya meşgul hatası

Mesaj gönderen ertank »

loaded yazdı: 18 Eki 2019 11:26 Benim bu tür asenkron durumlar için kullandığım basit bir yöntem denemekte fayda var
Bu kodun tek tehlikesi zaman aşımı kontrolü olmaması. Uygulamanın yanıt vermez hale gelmesine sebep olabilir.
Kullanıcı avatarı
loaded
Üye
Mesajlar: 122
Kayıt: 12 Eki 2010 09:45
Konum: Konya
İletişim:

Re: dosya meşgul hatası

Mesaj gönderen loaded »

// Yazma Okuma Fonksiyonu
// Yazma Okuma Fonksiyonu Sonu
Aralıklarına kullanıcı kendi kontrollerini koyabilir.
Ben kendi uygulamalarında

Kod: Tümünü seç

GetTickCount64
yöntemi ile zaman kontrolü yapmaktayım işlem sonunda

Kod: Tümünü seç

 Application.ProcessMessages
(Threadlarda farklı yöntemler uyguluyorum) ile de uygulamanın sürekli aktif olmasını sağlıyorum.
ertank yazdı: 18 Eki 2019 11:56 Bu kodun tek tehlikesi zaman aşımı kontrolü olmaması. Uygulamanın yanıt vermez hale gelmesine sebep olabilir.
Kalk ve işe yarar bir şey yap! Çünkü Allah (c.c.) yeniden başlayanların yardımcısıdır.
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

Re: dosya meşgul hatası

Mesaj gönderen duraumsa »

hata kodu bu hocam sabahtan beri çelışıyor 4 defa hata verdi

hata aynı hata
Cannot open file "C:\silim_setup\resim13.bmp".
The process cannot access the because it is begin used by another process.
Dosya ekleri
hata3 (1).jpg
hata3 (1).jpg (1.48 KiB) 2086 kere görüntülendi
duraumsa
Üye
Mesajlar: 27
Kayıt: 24 Eki 2015 01:54

Re: dosya meşgul hatası

Mesaj gönderen duraumsa »

s.a. üstad

proğramları sabaha kadar çalıştırdım yazma yapan proğram 7 defa aynı hatayı vermiş

okuma yapan proğram

aşağıdaki hatayı vermiş

HATA: Dosya okunamadı: C:\silim_setup\resim13.bmp
Orjinal Hata : Cannot open file "C:\silim_setup\resim13.bmp".
The process cannot access the file because it is being used by another process

Resim
Dosya ekleri
Screenshot_1.jpg
Screenshot_1.jpg (1.89 KiB) 2076 kere görüntülendi
ertank
Kıdemli Üye
Mesajlar: 1648
Kayıt: 12 Eyl 2015 12:45

Re: dosya meşgul hatası

Mesaj gönderen ertank »

duraumsa yazdı: 19 Eki 2019 07:56 proğramları sabaha kadar çalıştırdım yazma yapan proğram 7 defa aynı hatayı vermiş
Aleykümselam,

Program otomatik olarak mı dosyaya yazma yapıyor? Butonu gerçek bir kişi tıklamıyor mu?
Cevapla