Panel użytkownika
Nazwa użytkownika:
Hasło:
Nie masz jeszcze konta?

[SDL] Ogromne wykorzystanie pamięci

Ostatnio zmodyfikowano 2012-08-12 20:47
Autor Wiadomość
pjpeg_objected
Temat założony przez niniejszego użytkownika
[SDL] Ogromne wykorzystanie pamięci
» 2012-08-01 10:37:21
Witam . Mam problem z dużym wykorzystaniem pamięci w programie. Program podziała 20 - 40 sekund i się wyłącza. Wykorzystanie pamięci dochodzi nawet do 2 gb. Zamieszczam kod i prosiłbym o chociaż naprowadzenie mnie na dobrą drogę i jeśli można nie ocenianie estetyczności kodu bo dopiero się uczę. Z góry dziękuje :)

C/C++
//hfile.h

#include <SDL/SDL.h>

SDL_Surface * screen = NULL;
SDL_Surface * bg = NULL;
SDL_Surface * Circle = NULL;
SDL_Surface * Cross = NULL;
SDL_Rect Player;
SDL_Event event;


enum GAMESTATE { PLAY, WIN, DRAW };
enum PLAYER { CIRCLE, CROSS };

int Round = 0;

C/C++
#include <SDL/SDL.h>
#include "hfile.h"





void Init()
{
    SDL_Init( SDL_INIT_EVERYTHING );
    screen = SDL_SetVideoMode( 600, 600, 32, SDL_SWSURFACE );
    SDL_WM_SetCaption( "Kolko i Krzyzyk", NULL );
   
   
    bg = SDL_LoadBMP( "bg.bmp" );
    Circle = SDL_LoadBMP( "circle.bmp" );
    Cross = SDL_LoadBMP( "cross.bmp" );
    // SDL_SetColorKey(Circle, SDL_SRCCOLORKEY, SDL_MapRGB(Circle->format, 255, 255, 255 ) );
    // SDL_SetColorKey(Cross, SDL_SRCCOLORKEY, SDL_MapRGB(Cross->format, 255, 255, 255 ) );
   
    GAMESTATE GameState = PLAY;
    PLAYER Player = CIRCLE;
   
}

void Check( bool & Run )
{
    if( event.type == SDL_QUIT ) Run = false;
   
   
   
}

void Movement( bool & Run )
{
    if( event.type == SDL_KEYDOWN )
    {
        switch( event.key.keysym.sym )
        {
        case SDLK_RIGHT:
            Player.x += 205;
            break;
        case SDLK_LEFT:
            Player.x -= 205;
            break;
        case SDLK_UP:
            Player.y -= 205;
            break;
        case SDLK_DOWN:
            Player.y += 205;
            break;
        case SDLK_ESCAPE:
            Run = false;
            break;
        }
    }
   
}

void InEvent( bool & Run )
{
    while( SDL_PollEvent( & event ) )
    {
        Check( Run );
        Movement( Run );
    }
   
}



void Render()
{
    SDL_BlitSurface( bg, NULL, screen, NULL );
    if( Round % 2 == 0 )
         SDL_BlitSurface( Circle, NULL, screen, & Player );
   
    if( Round % 2 != 0 )
         SDL_BlitSurface( Cross, NULL, screen, & Player );
   
    SDL_Flip( screen );
   
}

void Quit()
{
    SDL_FreeSurface( bg );
    SDL_FreeSurface( Circle );
    SDL_FreeSurface( Cross );
    SDL_Quit();
}

C/C++
#include <SDL/SDL.h>
#include "tasks.cpp"

int main( int argc, char * argv[] )
{
    bool Run = true;
    while( Run == true )
    {
        Init();
        InEvent( Run );
        Render();
       
       
       
       
    }
    Quit();
    return 0;
}


Dodam jeszcze, że program dopiero zacząłem ale wolę wyeliminować problem teraz dopóki kod jest krótki.
P-61562
mostrom
» 2012-08-01 11:23:08
Funkcja Init powinna być przed pętlą główną. Teraz z każdą iteracją pętli przydzielasz pamięć dla kilku wskaźników, nie usuwając ostatnio przydzielonej. Stąd gigantyczny wyciek pamięci.
P-61567
pjpeg_objected
Temat założony przez niniejszego użytkownika
» 2012-08-03 00:31:25
Dziękuje bardzo za pomoc, co prawda był to głupi błąd ale nie potrafiłem go wypatrzeć. Teraz jednak mam kolejny problem i postanowiłem, że wkleję go tu bo nie chcę kolejnego tematu zakładać. Błędu przy kompilacji nie ma ale program włącza się i wyłącza, a w konsoli zwraca "Process returned 3". Oto kod:

C/C++
#include <SDL/SDL.h>

SDL_Surface * screen = NULL;
SDL_Surface * bg = NULL;
SDL_Surface * circle = NULL;
SDL_Surface * cross = NULL;
SDL_Event event;


class TicTacToe
{
private:
    int Map[ 9 ];
    int Round;
    int Player;
public:
    void Graph_Init();
    bool Check();
    void Handle_Input( bool & Run );
    void Render();
    bool Quit();
};

void TicTacToe::Render()
{
    SDL_BlitSurface( bg, NULL, screen, NULL );
    SDL_Flip( screen );
   
}

void TicTacToe::Graph_Init()
{
    SDL_Init( SDL_INIT_EVERYTHING );
    screen = SDL_SetVideoMode( 600, 600, 32, SDL_SWSURFACE );
    SDL_WM_SetCaption( "Tic Tac Toe", NULL );
    bg = SDL_LoadBMP( "bg.bmp" );
    circle = SDL_LoadBMP( "circle.bmp" );
    cross = SDL_LoadBMP( "cross.bmp" );
    SDL_SetColorKey( circle, SDL_SRCCOLORKEY, SDL_MapRGB( circle->format, 255, 255, 255 ) );
    SDL_SetColorKey( cross, SDL_SRCCOLORKEY, SDL_MapRGB( cross->format, 255, 255, 255 ) );
}

void TicTacToe::Handle_Input( bool & Run )
{
    if( event.type == SDL_QUIT ) Run = false;
   
    if( event.type == SDL_KEYDOWN )
    {
        switch( event.key.keysym.sym )
        {
        case SDLK_RIGHT:
           
            break;
        case SDLK_LEFT:
           
            break;
        case SDLK_UP:
           
            break;
        case SDLK_DOWN:
           
            break;
        case SDLK_ESCAPE:
            Run = false;
            break;
        case SDLK_RETURN:
            Round++;
            break;
        }
    }
}

C/C++
#include <SDL/SDL.h>
#include "functions.cpp"

int main( int args, char * argh[] )
{
    TicTacToe ttt;
    bool Run = true;
    ttt.Graph_Init();
    while( Run )
    {
        ttt.Render();
       
    }
    SDL_Quit();
    return 0;
}

Byłbym wdzięczny za jakąkolwiek pomoc.
P-61618
mostrom
» 2012-08-03 10:55:05
Źle pakujesz program w obiekty. SDL_Init() jest u ciebie wywoływana wewnątrz treści metody klasy, a SDL_Quit() wywołujesz wewnątrz treści funkcji main(). Takie rozplanowanie jest dodatkowo niekorzystne jeśli miałbyś dodać timery itd. Zrób sobie klasę okno, w której definiujesz wskaźnik ekran(screen), a SDL_Init() daj w main(), lub jakiejś globalnej funkcji wywoływanej w main(). Tak samo z SDL_Quit().
Twoja metoda HandleInput, też nie będzie działać, musisz w argumencie dać event, a nie bool Run. Zmienną Run przypisuj w funkcji main, lub w globalnej funkcji obsługującej pętlę eventów. Metoda klasy kółko i krzyżyk HandleInput lepiej niech obsługuje tylko to co jest związane z interfejsem gry.
Tyle ja bym zmienił.

A tak w ogóle to lepiej zakładaj nowy temat, bo taki tutaj zwyczaj^^
P-61626
pjpeg_objected
Temat założony przez niniejszego użytkownika
» 2012-08-10 22:57:33
I tu wychodzi to, że nie jestem doświadczony. Zawsze sądziłem, że do zmiennych globalnych mam dostęp zewsząd, nawet z klas. Dopiero zacząłem uczyć się programowania obiektowego praktycznie, co łatwo zauważyć. Jeśli chodzi o SDL_Quit() to zrobiłem to tylko tymczasowo, żeby sprawdzić czy Init też będzie działać jak dam go w main. Teraz nasuwa mi się pytanie. Co w takim kółko i krzyżyk zdefiniować jako klasę? I czy będę musiał wykorzystywać dziedziczenie? Jakieś dwa dni temu skończyłem kółko i krzyżyk bez klas, z menu, muzyką i padłem na robieniu SI. Udało mi się jedynie zrobić, że komputer wybiera puste pola, nic więcej. Próbowałem ogarnąć algorytm min-max ale nie do końca potrafiłem go zrozumieć a co gorsze przedstawić na kod źródłowy. I teraz takie pytania. Czy powinienem przerobić te kółko i krzyżyk na klasy, żeby trochę potrenować programowanie obiektowe i samo pojęcie klas? Czy normalnym jest, że nie potrafię napisać tak stosunkowo prostego algorytmu i czy powinienem teraz pisać kolejne projekty czy zostać na tym i dopracowywać/przerabiać go np. na klasy? Tutaj podaje linka do gry z kodem źródłowym. http://www.speedyshare.com/9TWFh/TTT-oFFix.rar
Usunąłem muzykę z powodu dużej wagi mp3. Za odpowiedź chociaż na jedno pytanie będę bardzo wdzięczny. Pozdrawiam.
P-62196
kamillo121
» 2012-08-12 12:26:13
Co w takim kółko i krzyżyk zdefiniować jako klasę? I czy będę musiał wykorzystywać dziedziczenie?
Te pytania świadczą o tym, że nie wiesz jeszcze co to tak naprawdę programowanie obiektowe.

Czy powinienem przerobić te kółko i krzyżyk na klasy, żeby trochę potrenować programowanie obiektowe i samo pojęcie klas?
To wszystko zależy od tego czy chcesz już teraz przejść na programowanie obiektowe. Jeżeli chcesz się tego uczyć to gra kółko i krzyżyk jest dobrym materiałem do ćwiczeń. Mała aplikacja którą można zaprojektować na kilka sposobów(mała ale  w cale nie prosta dla początkujących).


Czy normalnym jest, że nie potrafię napisać tak stosunkowo prostego algorytmu i czy powinienem teraz pisać kolejne projekty czy zostać na tym i dopracowywać/przerabiać go np. na klasy?
Jeżeli chodzi Ci o algorytm SI to w cale nie musi być prosty i nie poddawaj się tylko dlatego że go nie potrafisz zaprojektować czy oprogramować. Patrząc wstecz(analizując cudze pracę) śmiało mogę stwierdzić, że niektóre osoby tworzące "większe projekty" nie potrafiłyby napisać dobrze gry wspomnianej w temacie nie wspominając już o SI(i nie chce tu nikogo obrażać). Radzę Ci pozostać przy tym programie i napisać go na kilka sposobów, poćwiczyć na nim obiektowość. 
P-62306
pjpeg_objected
Temat założony przez niniejszego użytkownika
» 2012-08-12 14:40:01
Wiem, że na pewno powinienem zadeklarować jako obiekt gracza oraz planszę. Ale czy na przykład takie sprawdzanie czy ktoś wygrał albo menu, w którym będzie możliwość wyboru 1 lub 2 graczy też powinienem deklarować jako klasę? Nie chodzi mi o samą teorię o klasach tylko praktyczne ich wykorzystanie.
P-62318
kamillo121
» 2012-08-12 20:47:15
W praktycznie każdej sytuacji możesz użyć obiektów. Pytanie czy w danym momencie to będzie korzystne, czy nie stworzy to zbędnych narzutów, czy dany fragment ma być elastyczny(można i strukturalnie napisać w miarę elastyczny kod ale nie to jest istotą) i czy będzie kiedyś rozwijany, może używany w innym miejscu. Na tego typu pytania trzeba sobie odpowiedzieć. Na przykład takie menu. Menu może zawierać wiele funkcji i pozycji, może być używane w wielu kontekstach. Jest to dobry kandydat na klasę  ale to też zależy od zapotrzebowania. Jeżeli potrzebujesz prostego menu tylko w jednym miejscu z opcjami "start" i "quit" to nie jest to aż takie konieczne, żeby to upchać w klasę. Rozważ przypadek menu w bardziej rozbudowanej aplikacji. Aplikacja posiada menu główne,  każda kategoria z menu może posiadać swoje podmenu a każde podmenu w innej kategorii może posiadać kolejne drzewa kategorii. Jeżeli chciałbyś to ująć strukturalnie oczywiście się da. Czy to będzie dobry wybór ? Jeżeli potrafisz pisać zorientowany obiektowo kod to nie będzie najlepszym wyborem tworzenie tak wymagającego elementu strukturalnie. W tym wypadku kod napisany metodą oop będzie prawdopodobnie łatwiejszy w rozwijaniu, czytelniejszy no i bardziej elastyczny na zmiany pod warunkiem, że dobrze go przemyślisz. Klasa menu może spełniać role drzewa do którego można dopinać kolejne liście bądź inne gałęzie.
Idąc dalej, sprawdzanie statusu rozgrywki(wygrana/przegrana) można umieścić np. w funkcji składowej klasy rozgrywka która zawiera w sobie elementy dotyczące samej rozgrywki. Powiedzmy, że obiekt rozgrywka do poprawnego funkcjonowania potrzebuje danych jak: ilość graczy, odpowiednia ilość utworzonych graczy, np czas rozgrywki(o ile jest potrzebny) itd. Teraz nasuwa się odpowiedź na kolejne pytanie odnoście wyboru graczy. Drzewo menu zawiera w sobie dwie opcje "1 gracz", "2 graczy" (być może jest gałęzią innego drzewa menu które ma w sobie opcje start,opcje, wyjście), po wyborze powiedzmy opcji z menu "2 graczy" wywołuje zdarzenie które ma za zadanie utworzyć "rozgrywkę" z dwoma graczami(gdzie gracz to kolejny obiekt).
Tak dalej można projektować, tak by cały system działał logicznie i w miarę możliwości naturalnie.

Tutaj wyłania się problem projektowania, jeżeli sam programujesz i projektujesz to musisz jednocześnie poznawać programowanie obiektowe jak i projektowanie.
P-62363
« 1 »
  Strona 1 z 1