[PHP] dynamische 'uninclude' oid?

Pagina: 1
Acties:

Onderwerpen


Verwijderd

Topicstarter
hallo menschen van het goede leven;

ik heb een php irc botje gemaakt dat op de console draait (dus niet via apache), en in een endless loop blijft hangen, nu en dan kijkt of er iets gezegd is en daar dan iets mee doet. moet uiteindelijk een soort A.I. ding worden :)

nu is het nogal irritant dat ik bij elke verandering in het 'text-process' gedeelte het botje opnieuw moet starten ... bij elke kleine verandering in de php moettie weer opnieuw connecten e.d., dat is ook niet erg gewenst door de irc server admins i guess..

eigenlijk zou ik liever hebben dat die text-process functie in een aparte php komt, die dan door het botje - terwijl die aan het executen is, binnen de main loop - nu en dan opnieuw wordt ingelezen.

ik kan zeg maar in de endless loop iets doen als 'if (file=veranderd) include "ai_functions.php";' maar dat kan logischerwijs maar een keer. ik wil dus eigenlijk iets als 'if (file=veranderd) uninclude "ai_functions.php"; include "ai_functions.php"; maar een uninclude functie lijkt niet te bestaan :P

andere mogelijkheid is om een eigen ai-scripttaal te maken die door het botje kan worden geprocessed, maar dat is wel erg drastisch (lees: tijdrovend (hoewel wel erg leuk natuurlijk))

iemand suggesties?

*edit: bedenk me net nog een andere mogelijkheid: een 2e php script die via sockets met de bot communiceert. zou dat kunnen, of zie ik iets over het hoofd?

[ Voor 27% gewijzigd door Verwijderd op 23-09-2004 20:48 ]


  • kvdveer
  • Registratie: November 2000
  • Laatst online: 07-11-2023

kvdveer

Z.O.Z.

Uninclude kan niet. Het undefinen van functies kan ook niet. Wel kun je een volgende constructie gebruiken: (heb ik zelf ooit gedaan voor een irc-bot)
PHP:
1
2
3
4
5
6
$function = create_function( '$var1, $var2', '
  echo $var1;
  echo $var2;
');

$function('hallo!','DAG!');


Bij iedere keer dat je je functie aanmaakt vergeet 'ie de oude functie als het goed is. Helaas is het geheugenmanagement van PHP4 niet zo goed. Op deze manier loopt langzaam maar zeker je geheugen vol. PHP4 is eigenlijk niet geschikt om een deamon in te schrijven. Het ontbreekt gewoon aan een intelligente garbage collector.

Localhost, sweet localhost


  • NMe
  • Registratie: Februari 2004
  • Laatst online: 09-09 13:58

NMe

Quia Ego Sic Dico.

Waarom zou je willen unincluden? Je kan toch kijken welke file je wil includen voordat je daadwerkelijk wat include? Dan is unincluden niet eens meer nodig, omdat je die file niet eens geinclude hebt...

'E's fighting in there!' he stuttered, grabbing the captain's arm.
'All by himself?' said the captain.
'No, with everyone!' shouted Nobby, hopping from one foot to the other.


Verwijderd

Ik heb ook eens een modulaire IRC-Bot gemaakt waarvoor ik de module-bestanden in een variable $code las met file() en die dan vervolgens door eval($code) liet uitvoeren bij elke input-loop.

Het voordeel is dat je via IRC modules kunt uit- en aanzetten door je script te laten checken op iets als "!module unload <naam>", waarna de betreffende module uit $code verwijderd wordt en dus niet meer wordt uitgevoerd. Het nadeel is alleen wel dat eval() een relatief tijdrovende functie is.

Acties:
  • 0 Henk 'm!

  • Roa
  • Registratie: December 2002
  • Laatst online: 03-07-2024

Roa

Wat je ook kunt doen volgens mij (ik kan er helemaal naast zitten natuurlijk) is proberen van ai_functions.php een functie te maken. Functies kan je natuurlijk blijven aanroepen. Maar goed, dit is een vrij simpele/logische oplossing dus ik zal vast wel iets over het hoofd zien, anders had je dit vast al gedaan :P

Research is what I'm doing when I don't know what I'm doing.


Acties:
  • 0 Henk 'm!

Verwijderd

edit:
Volgens mij gaat dit nooit werken, zoals je het nu wilt. Als je het voor een tweede keer zou includen krijg je een error dat je functies al bestaan.

Wat je kan proberen is je functies dynamisch te maken.

Dan krijg je iets in deze richting:

[code=PHP]<?php
function foo() {
echo "In foo()<br>\n";
}

function bar( $arg = '' ) {
echo "In bar(); argument was '$arg'.<br>\n";
}

$func = 'foo';
$func();
$func = 'bar';
$func( 'test' );
?> [/code]
http://nl2.php.net/manual...ns.variable-functions.php

Je zou de functies in bijvoorbeeld een array kunnen zetten en de array veranderen oid.


Je kan ook classes gebruiken. Als je die om de paamayim-nekudotayim manier gebruikt heb je geen instances en kan je volgens mij includen zonder error.

PHP:
1
2
3
4
5
6
7
8
9
class Bla
{
   public static function foo()
   {
         // dingen
   }
}

Bla :: foo()

http://nl2.php.net/manual....paamayim-nekudotayim.php

[ Voor 54% gewijzigd door Verwijderd op 24-09-2004 08:17 ]


Acties:
  • 0 Henk 'm!

Verwijderd

NMe84 schreef op 23 september 2004 @ 21:34:
Waarom zou je willen unincluden? Je kan toch kijken welke file je wil includen voordat je daadwerkelijk wat include? Dan is unincluden niet eens meer nodig, omdat je die file niet eens geinclude hebt...
De file is al wel geinclude, maar veranderd..
Roa schreef op 24 september 2004 @ 00:38:
Wat je ook kunt doen volgens mij (ik kan er helemaal naast zitten natuurlijk) is proberen van ai_functions.php een functie te maken. Functies kan je natuurlijk blijven aanroepen. Maar goed, dit is een vrij simpele/logische oplossing dus ik zal vast wel iets over het hoofd zien, anders had je dit vast al gedaan :P
Het zijn al wel functies, maar de functies zijn veranderd dus hij wil ze opnieuw laden. Overigens grappig want de oplossing voor z'n probleem is juist het uit functies halen van z'n logica :)
Verwijderd schreef op 24 september 2004 @ 08:10:Je kan ook classes gebruiken. Als je die om de paamayim-nekudotayim manier gebruikt heb je geen instances en kan je volgens mij includen zonder error.
Maar hij wil de implementatie reloaden en ook een class met alleen static functies kun je geen twee keer loaden.


@Baz: De methode van kvdveer gaat wel werken. Wat je ook kunt doen is de body van elke functie in afzonderlijke bestanden zetten. In plaats van een functie-aanroep include je dan dat bestand. Zo gebruik je altijd de nieuwste versie van je implementatie. Wil je het toch via functies blijven doen dan kun je de signature in een ander bestand implementeren, deze een keer includen en in die "lege" functie alleen een include van het bijbehorende body bestand. Iets mooier qua scope enzo, weet je iig precies welke variabelen je tot je beschikking hebt.

PHP:
1
2
3
4
function ai_blaat($var1, $var2)
{
   include('ai_functions/blaat.php');
}


Snel is anders maargoed als dat boeide had je het vast in een fatsoenlijke taal gemaakt ;) (NOFI)

Acties:
  • 0 Henk 'm!

  • frickY
  • Registratie: Juli 2001
  • Laatst online: 18-09 14:42
Voordat je PHP bestand wordt uitgevoerd, wordt deze geparsed naar het geheugen. Tijdens het draaien wordt deze niet opnieuw geparsed. Alle includes ed. worden dus eenmalig geparsed, en als het eenmaal draait zou je de bestanden zelfs gewoon kunnen verwijderen terwijl PHP doordraait.
Je zult dus, zoals hierboven al is gezegd, met externe bestanden moeten werken welke je uitleest (readfile) en uit laat voeren als php (eval).

Acties:
  • 0 Henk 'm!

Verwijderd

frickY schreef op 24 september 2004 @ 12:16:
Voordat je PHP bestand wordt uitgevoerd, wordt deze geparsed naar het geheugen.
Oh, dat wist ik niet. Moet zeggen dat ik de CLI ook niet zovaak gebruik en er weinig kans is dat ik precies een file upload tussen twee includes in 1 page-request :) Maar wel handig om te weten iig.

Acties:
  • 0 Henk 'm!

  • kvdveer
  • Registratie: November 2000
  • Laatst online: 07-11-2023

kvdveer

Z.O.Z.

frickY schreef op 24 september 2004 @ 12:16:
Voordat je PHP bestand wordt uitgevoerd, wordt deze geparsed naar het geheugen. Tijdens het draaien wordt deze niet opnieuw geparsed. Alle includes ed. worden dus eenmalig geparsed, en als het eenmaal draait zou je de bestanden zelfs gewoon kunnen verwijderen terwijl PHP doordraait.
Je zult dus, zoals hierboven al is gezegd, met externe bestanden moeten werken welke je uitleest (readfile) en uit laat voeren als php (eval).
Wat je nu zegt is niet waar. PHP parst include's zodra 'ie ze tegen komt. Daardoor kun je ook variabelen gebruiken bij het includen - die variabelen hebben nog geen waarde at parsetime.
Waar jij mee in de war bent is require().

Maargoed - dit hele topic is een soort van onzin, want het geheugenmanagement van php4 is niet geschikt voor scriptjes die voor langere tijd runnen, omdat de garbagecollector zo simpel is. Hoe dat zit met PHP5 is mij niet bekend.

[ Voor 14% gewijzigd door kvdveer op 24-09-2004 14:14 ]

Localhost, sweet localhost


Acties:
  • 0 Henk 'm!

  • frickY
  • Registratie: Juli 2001
  • Laatst online: 18-09 14:42
Dat klopt ja.
Require's worden altijd geparsed, en de includes alleen wanneer nodig.
In het volgende voorbeeld wordt hij bijv. niet geparsed
PHP:
1
2
$a = "nee";
if($a == "ja") include 'blaat.php';

Een require zou wel geparset zijn.

Maar wat ik bedoelde te zeggen was dat als je bijvoorbeeld dit doet;
PHP:
1
for($i = 1; $i < 100; $i++) include 'blaat.php';

Het bestand blaat.php maar 1x geparst wordt. Mocht je een variabele setten in dit bestand wordt hij wel 100 keer opnieuw geset, maar als je het bestand halverwege de loop zou aanpassen zouden deze aanpassingen niet van toepassing zijn tijdens de run van dit script. En dat bedoelde de TS.

offtopic:
Include en require zijn, net als echo, statements. Gebruik dus niet include('xxx') maar include 'xxx' ;)

[ Voor 54% gewijzigd door frickY op 24-09-2004 19:34 ]


Acties:
  • 0 Henk 'm!

  • Olaf van der Spek
  • Registratie: September 2000
  • Niet online
Kun je niet alles wat je ontvangt in een database table zetten en die table in een ander script weer uitlezen?
Dan hoef je niet met sockets te werken en mis je ook niks als je processing script even offline is voor een update.

Acties:
  • 0 Henk 'm!

Verwijderd

Topicstarter
he mensen bedankt voor de reacties .. weinig tijd dus even kort:
als ik het goed snap zijn er wel mogelijkheden, maar 'lekken' de meesten geheugen .. hoe zit dat met de 'eval' functie, heeft die ook dat probleem?
Pagina: 1