Avatar billede jb00797 Nybegynder
07. april 2007 - 13:13 Der er 10 kommentarer og
1 løsning

Lidt hjælp til classes

Hey

Jeg er ved at lave en simpel chat server, og kunne godt bruge lidt hjælp til at finde ud af hvilken måde der er bedst er styr clienterne på. Det jeg har gjordt indtil videre er at jeg har lavet en class som hedder client. Når der kommer en ny client på server, så bliver der lavet et nyt objekt af classen client. I den class bliver der læst på socketen om der kommer nye besked fra brugeren, og er der det bliver det sendt tilbage til mit program, som derefter sender besked til alle objekter af classen client.

Min problem er at jeg ved ikke helt hvordan jeg skal holde styr på hvornår clients disconnecter fra min server.

Jeg har dette kode:
Clients = (client[]) Array.newInstance(client.class,200);
Så jeg har plads til 200 brugere, og sådan som min kode er ny, tilføjer nye clienter sådan her.
Clients[numberofclients]  = new client(socket, this);
Også bliver der lagt en til numberofclients hver gang. Det virker fint nok, men når en client disconnecter så er der jo bare et objekt af classen client der ikke bliver brugt til noget, hvordan kan jeg lave sådan jeg ved om den bliver brugt, og gør den ikke kan jeg tilføje en ny client der?

Mvh.
Søren
Avatar billede mikkelbm Nybegynder
07. april 2007 - 16:36 #1
Du må have et serverobjekt af en slags. Dette objekt kan du jo smide med ind i dine klienters contructor. Når du så fanger en SocketException kalder du en public metode på serveren, som så fjerner/nulstiller den pågældende klient.

En overbygning på ovenstående kunne være at lade serveren implementere et interface, som har en removeClient metode - og så er det dette interface klienten kender til.
Avatar billede mikkelbm Nybegynder
07. april 2007 - 16:39 #2
Alternativt kunne du på dit klient-objekt have en property der hedder noget a la:

isDisconnected()
{
  return isDisconnected;
}

Og variablen isDisconnected bliver sat hvis du fanger en SocketException.

På den måde ved du om den pågældende klien bliver brugt/har en forbindelse.

(jeg hælder mest til metode 1)
Avatar billede jb00797 Nybegynder
07. april 2007 - 17:07 #3
Det var også noget i den retning jeg havde tænkt mig, jeg vidste bare ikke helt hvordan jeg skulle holde øje med om der var en client på en given plads i mit array med clienter. Jeg har fået en ide til hvordan jeg kan gøre, jeg ved dog ikke hvor smart den er. Det jeg gør nu er jeg har lavet et int array(med navnet users) med ligeså mange pladser som der er i et mit client array. Når der kommer en ny client gør jeg sådan her:
for(int x = 0; x < MAX_CONS; x++) {
if(users[x] != 1) {
Clients[x]  = new client(socket, this, x);
users[x] = 1;
break;
}
Så jeg kigger i users om pladsen er tom, den er 0 hvis der ikke er en client, og 1 hvis der er en klient. Det virker fint nok men er det en god ide at kalde contructeren på min class flere gange?
For hvis der først connecter en client for han pladsen 0 i clients(clients[0]) og når han så disconnecter, og der kommer en ny så er pladsen 0 ledig og jeg kalder contructeren på den class igen. Kan man bare gøre det eller er det noget man skal være opmærksom på?

Mvh.
Søren
Avatar billede mikkelbm Nybegynder
07. april 2007 - 17:14 #4
Det eneste du skal være opmærksom på der er at få lukket eventuelle sockets og få afsluttet eventuelle tråde i klient-objektet, så de bliver garbage-collected.

Et alternativ til dit array kan jo være Collections - har du overvejet en ArrayList?

ArrayList<client> clients = new ArrayList<client>();

Den er dynamisk og du kan add'e og remove fra den som det passer dig. Den finder selv ud af at increase/decrease size på det bagvedliggende array.
Avatar billede mikkelbm Nybegynder
07. april 2007 - 17:16 #5
Og hvis du vil beholde dit maks-antal af connections, kan du jo bare tjekke på om længden på arraylisten overstiger maks.
Avatar billede jb00797 Nybegynder
07. april 2007 - 17:37 #6
Okay ja, så hvis jeg lukker socketsne og trådene så burder der ikke være noget problem?

Ja jeg kunne jo også bruge en arraylist, men hvordan får jeg mit objekt af classen ind i den?
clients.add(new client(socket, this, x)); ?
Hvis det er så simpelt, så tror jeg faktisk jeg vil gøre sådan.

Mvh.
Søren
Avatar billede mikkelbm Nybegynder
07. april 2007 - 18:20 #7
Det er så simpelt :)

Og den har også get og remove metoder. Jeg ville helt klart vælge en Collection-class fremfor arrays, hvis antallet af elementer jævnligt ændrer sig.

Og ja, jeg vil mene det er rigeligt at lukke sockets og tråde, men nu ved jeg jo ikke hvad du ellers har af ting i dine client-objekter.
Avatar billede mikkelbm Nybegynder
07. april 2007 - 18:23 #8
Og hvis du kører på mit løsningsforslag nr. 1 så er det jo bare at gøre følgende:

... Server

private ArrayList<client> clients = new ArrayList<client>();

//.. serverkode...

public void removeClient (client c)
{
  clients.remove(c);
}

... Klient

private Server server;

//.. klient-kode..

public void run()
{
  while (running)
  {
      try{//socket-code}
      catch (Exception e)
      {
        close();
      }
  }
}

public void close()
{
  running = false;
  // Luk alle resoures...
  server.removeClient (this);
}
Avatar billede jb00797 Nybegynder
07. april 2007 - 20:29 #9
Mange tak for hjælpen, lægger du ikke et svar? Så får du dine point.

Mvh.
Søren
Avatar billede mikkelbm Nybegynder
07. april 2007 - 23:54 #10
Kommer her...
Avatar billede jb00797 Nybegynder
08. april 2007 - 01:40 #11
Endnu engang tak for hjælpen :)
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Kurser inden for grundlæggende programmering

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester