[Çözüldü] Java ile Yaptığım Yılan Oyununda Performans Sorunu

Başlatan blacksnow, 17 Aralık 2014 - 22:47:11

« önceki - sonraki »

0 Üyeler ve 1 Ziyaretçi konuyu incelemekte.

blacksnow

Birkaç ay önce yapmıştım bu oyunu o zamanlar Windows kullanıyordum.Son bir aydır Ubuntu 14.04 kullanıyorum.Eclipse ile oyunu açtığımda hafif donmalar oluyor ve bu arada işlemci kullanımı %100 ' e çıkıyor.Windows'da iken hiç donma olmuyordu.Bu şekilde donmalar normal mi?Değilse neden böyle oluyor?

Ayrıca internette bulduğum bir oyunu denendim ve hiç donma olmadı.Acaba ben mi çok kötü kodladım oyunu?Karşılaştırma yapmak için iki oyununda linklerini veriyorum.
Cevaplarınız için şimdiden teşekkürler.

Bu internette bulduğum: https://github.com/PSNB92/SnakeRemake/tree/master/src/org/psnbtech
Bu da benim yaptığım: http://www.megafileupload.com/en/file/589079/SnakeGame-tar-gz.html

java -version çıktısı
java version "1.8.0_25"
Java(TM) SE Runtime Environment (build 1.8.0_25-b17)
Java HotSpot(TM) 64-Bit Server VM (build 25.25-b02, mixed mode)


Not:Bu sorunu aşmam lazım.Yani tekrar Windows kullanmak istemiyorum.


Mesaj tekrarı yüzünden mesajınız birleştirildi. Bu mesajın gönderim tarihi : 17 Aralık 2014 - 23:14:32

Konuyu açtıktan sonra oyunu bir de java-7-openjdk-amd64 ile denedim ve hiç kasmadan çalıştı.Fakat oyunda pause yaptığım zaman işlemci kullanımı %100 çıkıyor.Bilgisayar ısınmaya başlıyor.Bunun yazdığım kodlardan dolayı böyle olduğunu düşünüyorum.Yine de yorumlarınızı bekliyorum.

Amenofis

#1
Openjdk ile denedim. Benim dandik dizüstünde bile cpu %3. Diğer oyundan çok kopya çekmişsin bu yüzden koddaki hataları fark edemiyorsun. Gördüğüm kadarıyla senin kodunda tek kritik hata kare/sn oranının değişken olması.

Oyunda yılan büyüdükçe fps düşüyor. Bunun sebebi her kare arasında sabit 100 ms uyuması. Yılan büyüdükçe çizim işlemleri artar ve oyunda geçen süre de buna paralel artar. Fps nin sabit kalması için oyun süresi + bekleme süresinin sürekli aynı olması gerekir. Algoritma kabaca şöyle olmalı. Buna uyarsan pause sorunu da çözülür.

Diyelim 10 kare/sn hız istiyorsun. Yani her kare toplam 100 ms olacak.

void update()
{
// Klavyeyi oku
if(pause) return; // Duraklatılmış ise bu kareyi bitir.

// Duraklama yok. Oyun alanını yeniden çiz ve güncelle
}

while (!exit()) { // Oyuna devam ise

baslangic = zaman(); // Kare başlangıç anını al.
update();
bitis = zaman(); // Kare bitiş anını al.
gecen_sure = sureyiHesapla(baslangic, bitis);

Thread.sleep (100 - gecen_sure);
}

Bir de LinkedList yerine dizi tabanlı ArrayList gibi veri yapıları daha verimli çalışır. Hatta önceden bellek ayırırsan hepsinden hızlı olur. Mesela yılan en fazla kaç nokta olabilir? 50 diyelim.

Point[] snake = new Point[50];
int point_count = 1;
...
...
for(int n = 0; n < point_count; ++n)
    blabla (snake[n].x, snake[n].y);

blacksnow

Burda ekran çizimleri yenilenirken geçen süreyi ölçtüm ve 0 ile 1 ms arasında gidip geliyor.Sizce bu süre çok önemsenicek bir süre mi?Ayrıca pause yapıldığında 100 ms uyutmaya devam mı etmeliyim?Verdiğiniz algoritmada böyle yapmışsınız.Çünkü böyle yapmazsam işlemciyi sınırlamamış oluyorum.Yani son gücünde tarama yapıyor while döngüsünün içinde.
public void paintComponent(Graphics g) {
super.paintComponent(g);
long startTime = System.currentTimeMillis();
if (game.isGameStart || game.isGameOver) {
g.setColor(Color.GREEN);
for(Point snake : snake.snakeBody) {
g.fillRect((snake.x * 20) + 1 , (snake.y * 20) + 1, snakeSize, snakeSize);
}

g.setColor(Color.ORANGE);
g.fillOval((snake.food.x * 20) + 5, (snake.food.y * 20) + 5, 10, 10);
}
long endTime = System.currentTimeMillis();
long estimatedTime = endTime - startTime;
System.out.println(estimatedTime);
}

Birde şu cümleniz kafamı karıştırdı."Fps nin sabit kalması için oyun süresi + bekleme süresinin sürekli aynı olması gerekir."

Aslında fps-nin sabit kalması için bekleme süresi(100 ms) - oyun süresinin(yani çizim yapıldığı süre) sabit kalması gerekmiyor mu?

Amenofis

(Oyun süresi + bekleme süresi) demişim yani ikisinin toplamı.

Ben oynayınca yılanın gitgide yavaşladığını farkettim ama sebebini bilmiyorum. Çizim isterse 1 nanosaniye sürsün farketmez. Ben yaptığının yanlış olduğunu söylüyorum sadece. Bu şekilde yaparsan her makinada farklı hızlarda çalışır. Oyuna bişeyler ekledikçe yavaşlar. Grafik hızlandırıcı yoksa ne yapacaksın? Software render ile 100 kat daha yavaş olur çizimler. Her durum için, oyunu deneyecek herkes için farklı kod mu derleyeceksin?

Duraklamalarda tabiki bekleme şart. Yani oyunu oynarken %3 cpu kullanacak, durdurunca %100! Mantıklı geliyor mu?

blacksnow

Kesinlikle haklısınız her sistemde farklı sonuçlar verecektir.Her makineye göre kod yazmak elbette mantıksız.Pause konusunu da söylediğiniz şekilde çözdüm.Şuan da oyun stabil çalışıyor.Verdiğiniz fikirler için teşekkür ederim.