Strona 1 z 1

Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 14:48
przez Cyfrowy Baron
Zastanawiam się nad pewną możliwością.

Mam 6 obiektów typu TImage: Image1, Image2...Image6

i funkcję:

Kod: Zaznacz cały
void (TImage *Image)
{
// tutaj funkcja musi wykonać operacje na 6 obiektach typu TImage
}


Funkcja nie należy do klasy formularza, znajduje się w zupełnie innym pliku i nie ma pojęcia jakie obiekty znajdują się na formularzu. Jedyny jej kontakt z formularzem to ta funkcja.

Czy istnieje jakaś możliwość przekazania 6 obiektów do funkcji jako pojedynczy argument?
Tym samym takie rozwiązanie nie wchodzi w grę:

Kod: Zaznacz cały
void (TImage *Image1, TImage *Image2, TImage *Image3, TImage *Image4, TImage *Image5, TImage *Image6)
{
}

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 15:46
przez Witold
Cyfrowy Baron napisał(a):Czy istnieje jakaś możliwość przekazania 6 obiektów do funkcji jako pojedynczy argument?

Może tablica (dla której koniec danych to NULL) ?

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 16:07
przez kinio
Hej!

Cyfrowy Baron napisał(a):Funkcja nie należy do klasy formularza, znajduje się w zupełnie innym pliku i nie ma pojęcia jakie obiekty znajdują się na formularzu. Jedyny jej kontakt z formularzem to ta funkcja.

Trochę niejasno napisane, ale mniemam że chodzi o to aby wysłać do funkcji 6 obiektów naraz.
Jeżeli tak to można to zrobić na dwa sposoby:

1. Stworzyć tablicę:
Kod: Zaznacz cały
TImage** tab[] = {Image1, Image2, Image3, Image4, Image5, Image6}

a później napisać funkcję:
Kod: Zaznacz cały
void func(TImage** tab)
{
    for(int i=0;i<6;++i)
    {
         //operacje na kazdym Image. Odnosimy się poprzez tab[i] np.
         tab[i]->Left = 0;
    }
}

Funckję oczywiście można łatwo uogólnić dla dowolnej liczby komponentów. Jeżeli zamierzamy przesyłać tablicę o różnej wielkości to trzeba podać jej rozmiar np:
Kod: Zaznacz cały
void func(int size, TImage** tab)
{
    for(int i=0;i<size;++i)
    {
         //operacje na kazdym Image. Odnosimy się poprzez tab[i] np.
         tab[i]->Left = 0;
    }
}


2. Stworzyć funkcję o zmiennej liczbie argumentów:
Kod: Zaznacz cały
#include <stdarg.h>
...
void func(int liczba, ...)
{
     va_list vl;
     va_start(vl, liczba);

     for(int i=0;i<liczba;++i)
     {
          TImage* img = va_arg(vl, TImage*);
          img->Left = 0;
     }

     va_end(vl);
}

No i funckje teraz możemy wywołać tak:
Kod: Zaznacz cały
func(6, Image1, Image2, Image3, Image4, Image5, Image6)


Mam nadzieje że to rozwiązuje problem. Jeżeli źle zrozumiałem powyższe Twoje zdanie to opisz dokładniej o co chodzi.

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 16:23
przez Cyfrowy Baron
TImage** tab[] = {Image1, Image2, Image3, Image4, Image5, Image6}


To nie działa. Komunikaty błędów:

[BCC32 Error] Main.cpp(151): E2034 Cannot convert 'TImage *' to 'TImage * *'
[BCC32 Error] Main.cpp(153): E2034 Cannot convert 'TImage * * *' to 'TImage * *'
[BCC32 Error] Main.cpp(153): E2342 Type mismatch in parameter 'tabImages' (wanted 'TImage * *', got 'TImage * * *')
[BCC32 Error] Main.cpp(162): E2034 Cannot convert 'TImage *' to 'TImage * *'
[BCC32 Error] Main.cpp(164): E2034 Cannot convert 'TImage * * *' to 'TImage * *'
[BCC32 Error] Main.cpp(164): E2342 Type mismatch in parameter 'tabImages' (wanted 'TImage * *', got 'TImage * * *')




Fragment mojego programu.

w pliku modułu DataCreate.h i DataCreate.cpp:
Kod: Zaznacz cały
public:
       void __fastcall UnPack(String NameGat, String NameTitle,
                         TStrings *ListaOpisu, TImage** tabImages);
//========================================================================
void __fastcall TCreateBase::UnPack(String NameGat, String NameTitle,
     TStrings *ListaOpisu, TImage** tabImages)
{
::SetCursor(LoadCursor(NULL, IDC_WAIT));
String packFileName = FBaseDir + "\\" + NameGat + "\\" + NameTitle + ".bfb";

TMemoryStream *mStream = new TMemoryStream();

Archiver->FileName = packFileName;
Archiver->OpenArchive(fmOpenRead);
Archiver->Password = "password";

Archiver->ExtractToStream("title.txt", mStream);
mStream->Position = 0;
ListaOpisu->LoadFromStream(mStream);
mStream->Position = 0;

for(int i = 0; i < 6; i++)
{
  WideString aFileName = "title" + (String)(i + 1) + ".jpg";
  try
  {
  Archiver->ExtractToStream(aFileName, mStream);

   mStream->Position = 0;

   std::auto_ptr<TJPEGImage> JImage(new TJPEGImage());
   JImage->LoadFromStream(mStream);
   tabImages[i]->Picture->Assign(JImage.get());

   mStream->Position = 0;
  }catch(...){;}
}

Archiver->CloseArchive();

delete mStream;
Screen->Cursor = crDefault;
}


w pliku modułu Main.cpp:
Kod: Zaznacz cały
TImage** tabImages[] = {Image1, Image2, Image3, Image4, Image5, Image6};

CreateGroup->UnPack("GAT1", "title1", ListaOpisu, tabImages);
Memo1->Lines->Assign(ListaOpisu);

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 16:29
przez kinio
Sorki, prosta literówka:
zamiast:
Kod: Zaznacz cały
TImage** tab[] = {Image1, Image2, Image3, Image4, Image5, Image6}

powinno być:
Kod: Zaznacz cały
TImage* tab[] = {Image1, Image2, Image3, Image4, Image5, Image6}

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 16:32
przez Cyfrowy Baron
Pierwsze co zrobiłem gdy nie zadziałało, to właśnie to, ale tak też nie działa:

Komunikaty błędu:

[BCC32 Error] Main.cpp(153): E2034 Cannot convert 'TImage * *' to 'TImage *'
[BCC32 Error] Main.cpp(153): E2342 Type mismatch in parameter 'tabImages' (wanted 'TImage *', got 'TImage * *')
[BCC32 Error] Main.cpp(164): E2034 Cannot convert 'TImage * *' to 'TImage *'
[BCC32 Error] Main.cpp(164): E2342 Type mismatch in parameter 'tabImages' (wanted 'TImage *', got 'TImage * *')




Siedzę już nad tym 8 godzin i jestem zmęczony...

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 16:33
przez Cyfrowy Baron
Już wiem co jest nie tak. funkcja musi mieć zdefiniowany rozmiar tablicy:

Kod: Zaznacz cały
void __fastcall UnPack(String NameGat, String NameTitle,
                         TStrings *ListaOpisu, TImage* tabImages[]);


Dzięki, to mi usprawnia całą aplikację, gdyż bez obiektów pośrednich funkcja działa szybciej, a juz zabierałem się za tworzenie specjalnej klasy, która będzie pośredniczyć w przekazywaniu obiektów. Jestem już chyba bardzo zmęczony, bo rozważałem możliwość użycia tablicy, ale uznałem, że to nie wypali...

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: poniedziałek, 9 marca 2009, 16:38
przez kinio
Spox!
Lepiej odpocznij :s

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: wtorek, 10 marca 2009, 22:49
przez Corvis
A próbowałeś wrzucić to do Listy obiektów ? TObjectList* ???

Re: Przekazywanie wielu obiektów jako jeden argument funkcji.

Nowy postNapisane: środa, 11 marca 2009, 11:39
przez Cyfrowy Baron
Problem jest już rozwiązany, wystarczy mi tablica.