• programmēšana,
  • Paralēlā programmēšana
  • Nesen izmēģināju pthreadus un biju patīkami pārsteigts – šis ir paplašinājums, kas PHP pievieno iespēju strādāt ar vairākiem reāliem pavedieniem. Nekādas emulācijas, nekādas maģijas, nekādu viltojumu — viss ir īsts.



    Es skatos uz šo jautājumu. Ir uzdevumu kopums, kas ātri jāpabeidz. PHP ir citi rīki šīs problēmas risināšanai, tie šeit nav minēti, raksts ir par pthreadiem.



    Kas ir pthreads

    Tas ir viss! Nu, gandrīz viss. Patiesībā ir kaut kas, kas var apbēdināt zinātkāro lasītāju. Nekas no tā nedarbojas standarta PHP, kas kompilēts ar noklusējuma opcijām. Lai izbaudītu vairākpavedienu izmantošanu, jūsu PHP ir jāiespējo ZTS (Zend Thread Safety).

    PHP iestatīšana

    Tālāk PHP ar ZTS. Ignorēt tik lielu izpildes laika atšķirību salīdzinājumā ar PHP bez ZTS (37,65 pret 265,05 sekundes), es nemēģināju vispārināt PHP iestatījumus. Gadījumā, ja nav ZTS, man, piemēram, ir iespējots XDebug.


    Kā redzat, izmantojot 2 pavedienus, programmas izpildes ātrums ir aptuveni 1,5 reizes lielāks nekā lineāra koda gadījumā. Lietojot 4 pavedienus - 3 reizes.


    Varat pamanīt, ka, lai gan procesors ir 8 kodolu, programmas izpildes laiks gandrīz nemainījās, ja tika izmantoti vairāk nekā 4 pavedieni. Šķiet, ka tas ir saistīts ar to, ka manam procesoram ir 4 fiziskie kodoli.. Skaidrības labad diagrammas veidā attēloju plāksni.


    Kopsavilkums

    PHP pieļauj diezgan elegantu daudzpavedienu izmantošanu, izmantojot paplašinājumu pthreads. Tas nodrošina ievērojamu veiktspējas pieaugumu.

    Tagi:

    • php
    • pthreads
    Pievienojiet atzīmes

    Rakstā ir aprakstīta vairāku pieprasījumu organizēšana, izmantojot PHP rīkus, izmantojot cURL bibliotēku. Šis mehānisms ir paredzēts, lai izveidotu skriptus, kas veic automatizētus pieprasījumus dažādiem tīmekļa serveriem.

    Savā praksē tīmekļa pārziņiem bieži ir jāizmanto programmatūras roboti, kas veic regulārus vai lielapjoma pieprasījumus tīmekļa lapām, aizpilda reģistrācijas veidlapas vai veic citas līdzīgas darbības. Tradicionāli un diezgan pamatoti šim nolūkam tiek izmantota PHP valoda un cURL bibliotēka, kas ir instalēta gandrīz visos tīmekļa serveros. CURL bibliotēka faktiski ir ligzdu pārklājums un ir tikai ērti lietojams pakalpojums http pieprasījuma ģenerēšanai atkarībā no programmētāja norādītajiem parametriem.

    Gadījumos, kad ir jāiesniedz pieprasījums vienam tīmekļa serverim, pietiek ar parastajiem cURL rīkiem, taču, ja jums ir jāģenerē liels skaits tīmekļa pieprasījumu, daudzpavedienu mehānisma izmantošana var ievērojami palielināt veiktspēju un paātrināt. scenārijs.

    Pirms es sāku aprakstīt skripta izstrādes mehānismu, pirmkārt, ko es domāju ar daudzpavedienu. Šeit runa ir par to, ka PHP faktiski nav daudzpavedienu, un kad termins " daudzpavedienu» attiecībā uz cURL bibliotēku, tad mēs runājam par multivaicājumi.

    Vairāku pieprasījumu mehānisms slēpjas apstāklī, ka, sūtot pieprasījumus uz tīmekļa serveriem, PHP negaida atbildi no katra secīgi nosūtītā pieprasījuma, bet nosūta (atkal pēc kārtas) vairākus pieprasījumus vienlaikus un pēc tam apstrādā atbildes. nāk no viņiem. Tāpēc ir jēga izmantot multithreading tikai tad, ja pieprasījumi tiek veikti dažādiem serveriem - ja jums ir nepieciešams veikt lielu pieprasījumu skaitu vienam serverim, tad vairāku pavedienu izmantošana nedos ievērojamu skripta veiktspējas pieaugumu.

    Tūlīt gribu atzīmēt, ka rīku darbam ar daudzpavedienu cURL ir ļoti maz, taču pat ar tiem, kas ir pieejami, jūs varat organizēt pilnvērtīgu darbu ar vairākiem pieprasījumiem.

    Tātad, tagad par praksi... Apsveriet piemēru, kad jāielādē liels skaits tīmekļa lapu, piemēram, lai pārbaudītu, vai tajās nav atpakaļsaites koda. Šim nolūkam jums būs nepieciešams:

    1. Ievietojiet visu URI sarakstu masīvā
    2. Izveidojiet “parasto” cURL masīvu vajadzīgajā daudzumā (pavedienu skaitā) un vienu cURL_multi.
    3. Inicializējiet katru izveidoto cURL (URL no iepriekš sagatavotā masīva, publicējiet mainīgos, ja nepieciešams, starpniekserveri utt.)
    4. Pievienojiet katru cURL vietrādim cURL_multi
    5. Sāciet visus pavedienus, izsaucot cURL_multi
    6. Cilpā mēs aptaujājam cURL_multi stāvokli un, ja ir pabeigts pavediens, apstrādājam saņemto lapu un tās vietā palaižam jaunu cURL. Ja URI saraksts ir beidzies, mēs apstrādājam tikai rezultātu. Cilpa turpinās tik ilgi, kamēr ir vismaz viens nepabeigts pavediens.
    7. Aizvērt visus cURL.

    Tagad faktiski skripts, kas veic šo darbību:

      funkcija Parsēt(&$urls ,$flowcount ) (

      // $urls ir masīvs ar URL

      // $flowcount - plūsmu skaits

      //Sākt pavedienus

      $ch =masīvs() ;

      $lcount0 =skaits ($urls ) ;

      if ($flowcount >$lcount0 ) $flowcount =$lcount0 ;

      for ($plūsma =0 ;$plūsma<$flowcount ;$flow ++) $ch =curl_ini(array_pop ($urls ) ) ; //izveidot cURL masīvu

      $mh =curl_multi_init() ; //izveidot cURL_multi

      for ($plūsma =0 ;$plūsma<$flowcount ;$flow ++) { //Šī cilpa inicializē cURL

      curl_setopt($ch [ $flow ] ,CURLOPT_REFERER,'TESTREFERER') ;

      curl_setopt($ch [ $flow ] ,CURLOPT_USERAGENT,” ) ;

      curl_setopt($ch [ $flow ] ,CURLOPT_RETURNTRANSFER,1 );

      curl_setopt($ch [ $flow ] ,CURLOPT_POST,1 );

      curl_setopt($ch [ $flow ] ,CURLOPT_POSTFIELDS,'TEST=TESTVAR') ;

      curl_setopt($ch [ $flow ] ,CURLOPT_COOKIE,'TEST=TESTCOOKIE') ;

      curl_multi_add_handle($mh ,$ch [ $flow ] ) ;

      $plūsmas =null ;

      darīt ( //Galvenā cilpa, turpinās tik ilgi, kamēr darbojas vismaz viens pavediens

      do curl_multi_exec($mh,$flows) ; while ($flows ==$flowcount ) ; //cikliski pārbaudiet darbojošos pavedienu skaitu

      $info =curl_multi_info_read($mh ) ;

      if (!count ($urls ) ) ( //Vairs nav jāapstrādā URL

      curl_close($info [ 'rokturis' ] ) ;

      $flowcount-;

      ) cits ( //Ir vairāk apstrādājamo vietrāžu URL

      curl_setopt($info [ 'rokturis' ] ,CURLOPT_URL,array_pop ($urls ) ) ;

      $res =curl_multi_getcontent($info [ 'rokturis' ] ) ;

      curl_multi_remove_handle($mh ,$info [ 'rokturis' ] ) ;

      Koda tekstā ir pietiekami daudz komentāru, lai saprastu, kas notiek. Ļaujiet man paskaidrot dažas lietas...

      1. Izsaukums curl_multi_init ir jāpadara OBLIGĀTS pēc tam, kad ir inicializēti visi “parastie” cURL, t.i. jūs nevarat apmainīt 9. un 10. rindu, tāpēc koda sadaļas $ch inicializācijai un nepieciešamo parametru iestatīšanai ir atdalītas.

      2. Katru reizi, kad curl_multi_exec tiek izsaukts 22. rindā, aktīvo plūsmu skaits tiek ievietots mainīgajā $flows, kas pēc tam tiek salīdzināts ar tekošo plūsmu skaitu (mainīgais $flowcount samazināsies, ja sarakstā vairs nebūs ierakstu apstrādāto URL (masīvs $urls)).

      3. curl_multi_info_read atgriež informāciju par nākamo pabeigto pavedienu vai false, ja kopš iepriekšējās šīs funkcijas izsaukuma nav notikušas izmaiņas.

      4. Funkcija curl_multi_info_read atjaunina datus, kas ievietoti mainīgajā $info, tikai pēc curl_multi_exec izpildes, tāpēc katras straumes apstrādei ir jāizmanto abas funkcijas.

      5. Lai pievienotu jaunu pavedienu, jums ir nepieciešams secīgi izsaukt trīs funkcijas: curl_multi_remove_handle, curl_multi_add_handle un curl_multi_exec.

      Visbeidzot, dažreiz ir svarīgi zināt papildu informāciju, kas saistīta ar apstrādājamo straumi. Šajā gadījumā var izveidot asociatīvu masīvu, kura atslēgas būs straumes identifikatori, t.i. vērtības sadaļā $info['handle'].

    Programmēšanā pastāvīgi jāstrādā ar dažādiem resursiem: failiem, ligzdām, http savienojumi. Un tiem visiem ir sava veida piekļuves saskarne, kas bieži vien nav saderīga. Tāpēc, lai novērstu šīs neatbilstības un vienotu darbu ar dažādiem datu avotiem, sākot ar PHP 4.3 tika izgudroti PHP Streams - straumes.

    Lai gan PHP 4.3 iznāca sen, daudzi PHP programmētāji ir ļoti maz priekšstata par straumes PHP, un turpiniet lietot CURL visur, lai gan PHPšim nolūkam ir ērtāka alternatīva formā Straumes konteksts.

    Pastāv tālāk norādītie straumju veidi PHP:

    • Fails cietajā diskā;
    • HTTP savienojums ar tīmekļa vietni;
    • Savienojums UDP ar serveri
    • ZIP fails;
    • Fails* .mp3.

    Kas visiem šiem resursiem ir kopīgs? Tos visus var lasīt un rakstīt, ti. tos visus var lasīt un rakstīt. Spēks PHP straumes būtība ir tāda, ka varat piekļūt visiem šiem resursiem, izmantojot vienu un to pašu funkciju kopu. Tas ir ļoti ērti. Turklāt, ja rodas vajadzība, varat uzrakstīt savu pavedienu apstrādātāja ieviešanu "straumes iesaiņotājs". Papildus lasīšanai un rakstīšanai, straumes PHPļauj veikt arī citas darbības, piemēram, pārdēvēšanu un dzēšanu.

    Programmēšana ieslēgta PHP, Jūs jau esat sastapies ar plūsmām, lai gan, iespējams, neesat par to uzminējis. Tātad funkcijas, kas darbojas ar straumēm, ir fopen (), file_get_contents(), fails () utt. Tātad faktiski jūs jau visu šo laiku izmantojat failu straumes, pilnīgi caurspīdīgi.

    Lai strādātu ar cita veida straumi, jānorāda tā protokols (iesaiņojums)šādā veidā: wrapper://some_stream_resource, Kur iesaiņojums://- tas ir, piemēram http://, file://, ftp://, zip:// utt., un some_stream_resource - URI, norāda, ko vēlaties atvērt. URI neuzliek nekādus formāta ierobežojumus. Piemēri:

    • http://website/php-stream-introduction.html
    • file://C:/Projects/rostov-on-don.jpg
    • ftp://lietotājs: [aizsargāts ar e-pastu]/pub/file.txt
    • mpeg://file:///music/song.mp3
    • data://text/plain;base64,SSBsb3ZlIFBIUAo=

    Tomēr, lūdzu, ņemiet vērā, ka ne visi protokoli un apstrādātāji var jums darboties, jo dažu čaulu atbalsts ir atkarīgs no jūsu iestatījumiem. Tāpēc, lai uzzinātu, kuri protokoli tiek atbalstīti, jums jāpalaiž šāds skripts:

    // reģistrēto kontaktligzdu transportu saraksts
    print_r(stream_get_transports());

    // reģistrēto pavedienu saraksts (apstrādātāji)
    print_r(stream_get_wrappers());

    // reģistrēto filtru saraksts
    print_r(stream_get_filters();

    PHP straumes konteksti

    Bieži http pieprasījumam ir jānorāda papildu parametri. Plūsmas konteksti atrisina šo problēmu, ļaujot norādīt papildu opcijas. Daudzām funkcijām, kas atbalsta pavedienu veidošanu, ir izvēles pavediena konteksta parametrs. Apskatīsim funkciju file_get_contents():

    Virkne file_get_contents(virkne $faila nosaukums [, int $flags = 0 [, resurss $konteksts [, int $offset = -1 [, int $maksimālais = -1]]]])

    Kā redzat, pavediena konteksts tiek nodots kā trešais parametrs. Konteksti tiek izveidoti, izmantojot funkciju stream_context_create(), kas aizņem masīvu un atgriež konteksta resursu.

    $options = masīvs(
    "http" => array(
    "method" => "GET",
    "header" => "Pieņemt valodu: en\r\n".
    "Sīkfails: foo = bārs\r\n"
    );

    $konteksts = straume_konteksts_izveidot($opcijas);

    // Izmantojot šo failu ar file_get_contents ...
    echo file_get_contents("http://www.example.com/", 0, $konteksts);

    Tātad šodien mēs uzzinājām, kas ir pavedieni un pavedienu konteksti PHP, apskatīja to izmantošanas piemērus, un nākamajos rakstos mēs runāsim par straumes metadatiem un izveidosim savu apdarinātāju.

    Dažreiz rodas nepieciešamība veikt vairākas darbības vienlaikus, piemēram, pārbaudīt izmaiņas vienā datu bāzes tabulā un veikt izmaiņas citā. Turklāt, ja kāda no operācijām (piemēram, izmaiņu pārbaude) aizņem ilgu laiku, ir acīmredzams, ka secīga izpilde nenodrošinās resursu līdzsvarošanu.

    Lai atrisinātu šādas problēmas, programmēšana izmanto multithreading - katra darbība tiek ievietota atsevišķā pavedienā ar atvēlētu resursu daudzumu un darbojas tajā. Izmantojot šo pieeju, visi uzdevumi tiks veikti atsevišķi un neatkarīgi.

    Lai gan PHP neatbalsta daudzpavedienu izmantošanu, ir vairākas tās atdarināšanas metodes, kas tiks apspriestas tālāk.

    1. Palaižot vairākas skripta kopijas — viena kopija katrai darbībai

    //woman.php if (!isset($_GET["pavediens"])) ( system("wget"http://localhost/woman.php?thread=make_me_happy"); system("wget ​​​​http: //localhost/ woman.php?thread=make_me_rich"); ) elseif ($_GET["pavediens"] == "make_me_happy") ( make_her_happy(); ) elseif ($_GET["pavediens"] == "make_me_rich") ) ( atrast_citu_vienu( ); )

    Kad mēs izpildām šo skriptu bez parametriem, tas automātiski palaiž divas sevis kopijas ar operāciju ID ("thread=make_me_happy" un "thread=make_me_rich"), kas ierosina nepieciešamo funkciju izpildi.

    Tādējādi mēs sasniedzam vēlamo rezultātu - vienlaikus tiek veiktas divas operācijas -, taču tas, protams, nav vairāku vītņu veidošana, bet vienkārši kruķis uzdevumu veikšanai vienlaikus.

    2. Path of the Jedi - izmantojot PCNTL paplašinājumu

    PCNTL ir paplašinājums, kas ļauj pilnībā strādāt ar procesiem. Papildus pārvaldībai tas atbalsta ziņojumu sūtīšanu, statusa pārbaudi un prioritāšu iestatīšanu. Šādi izskatās iepriekšējais skripts, izmantojot PCNTL:

    $pid = pcntl_fork(); if ($pid == 0) ( make_her_happy(); ) elseif ($pid > 0) ( $pid2 = pcntl_fork(); if ($pid2 == 0) ( atrast_citu_vienu(); ) )

    Izskatās diezgan mulsinoši, ejam rindu pēc rindas.

    Pirmajā rindā mēs "dakšām" pašreizējo procesu (dakša - procesa kopēšana no visu mainīgo vērtību saglabāšanas), sadalot to divos procesos (pašreizējais un bērns), kas darbojas paralēli.

    Lai saprastu, kur mēs šobrīd atrodamies bērna vai vecāka procesā, funkcija pcntl_fork atgriež 0 bērnam un procesa ID vecākam. Tāpēc otrajā rindā skatāmies uz $pid, ja tā ir nulle, tad esam bērnprocesā - izpildām funkciju, pretējā gadījumā esam vecākajā (4. rinda), tad izveidojam citu procesu un izpildām uzdevumu tādā pašā veidā.

    Skripta izpildes process:

    Tādējādi skripts izveido vēl 2 bērnprocesus, kas ir tā kopijas, satur tos pašus mainīgos ar līdzīgām vērtībām. Un ar funkcijas pcntl_fork atdotā identifikatora palīdzību tiekam vadīti, kurā straumē šobrīd atrodamies, un veicam nepieciešamās darbības.

    Vai ir reāls veids, kā ieviest daudzpavedienu modeli PHP, vai tas ir īsts, vai tas ir tikai tā atdarināšana. Pirms kāda laika tika ierosināts, ka varat piespiest operētājsistēmu ielādēt citu PHP izpildāmā faila gadījumu un apstrādāt citus vienlaikus notiekošus procesus.

    Problēma ir tāda, ka tad, kad PHP kods pabeidz PHP instances izpildi, tas paliek atmiņā, jo nav iespējas to iznīcināt no PHP. Tātad, ja simulējat vairākus pavedienus, varat iedomāties, kas notiks. Tāpēc es joprojām meklēju veidu, kā izveidot vairākus pavedienus, ko varētu efektīvi vai efektīvi atdarināt no PHP. Kādas idejas?

    Daudzpavedienu izveide ir iespējama php

    Jā, jūs varat daudzpavedienu PHP ar pthreads

    No PHP dokumentācijas:

    pthreads ir uz objektu orientēta API, kas nodrošina visus rīkus, kas nepieciešami daudzpavedienu veidošanai PHP. PHP lietojumprogrammas var izveidot, lasīt, rakstīt, izpildīt un sinhronizēt ar Threads, Workers un Threaded.

    Brīdinājums. Paplašinājumu pthreads nevar izmantot tīmekļa servera vidē. Tāpēc PHP pavedieniem jāpaliek uz CLI balstītās lietojumprogrammās.

    vienkāršs tests

    #!/usr/bin/phparg = $arg; ) publiskā funkcija palaist() ( if ($this->arg) ( $sleep = mt_rand(1, 10); printf("%s: %s -start -sleeps %d" . "\n", date(" g:i:sa"), $this->arg, $sleep); sleep($sleep); printf("%s: %s -finish" . "\n", date("g:i:sa" ), $this->arg); ) ) ) // Izveidojiet masīvu $steck = array(); //Initiate Multiple Thread foreach (range("A", "D") kā $i) ( $steck = new AsyncOperation($i); ) // Sākt The Threads foreach ($steck kā $t) ( $t- >sākt(); ) ?>

    Pirmais skrējiens

    12:00:06pm: A -sāk -guļ 5 12:00:06: B -sāk -guļ 3 12:00:06: C -sāk -guļ 10 12:00:06: D -sāk -guļ 2 12: 00:08: D finišs 12:00:09: B finišs 12:00:11: A finišs 12:00:16: C finišs

    Otrais brauciens

    12:01:36: A -sākt - guļ 6 12:01:36: B -sāk -guļ 1 12:01:36: C -start -sleeps 2 12:01:36pm: D -start -guļ 1 12: 13:37: B finišs 12:01:37: D finišs 12:01:38: C finišs 12:01:42: A finišs

    Reālās pasaules piemērs

    kļūdu_ziņošana (E_ALL); klase AsyncWebRequest paplašina pavedienu (publisks $url; publiskie $dati; publiska funkcija __construct($url) ( $this->url = $url; ) publiskā funkcija run() (if (($url = $this->url)) ( /* * Ja tiek pieprasīts liels datu apjoms, iespējams, vēlēsities * fsockopen un starp lasīšanas reizēm nolasīt, izmantojot usleep */ $this->data = file_get_contents($url); ) else printf("Pavediens #%lu netika sniegts URL\n", $this->getThreadId()); ) ) $t = mikrolaiks(true); $g = new AsyncWebRequest(sprintf("http://www.google.com/?q=%s", rand() * 10)); /* sākas sinhronizācija */ if ($g->start()) ( printf("Pieprasījuma sākumam vajadzēja %f sekundes ", microtime(true) - $t); while ($g->isRunning()) ( atbalss "."; usleep(100); ) if ($g->join()) ( printf(" un %f sekundes, lai pabeigtu %d baitu saņemšanu\n", microtime(true) - $t, strlen($g ->data)); ) else printf(" un %f sekundes līdz pabeigšanai, pieprasījums neizdevās\n", microtime(true) - $t); )

    kāpēc tu neizmanto popen ?

    For ($i=0; $i<10; $i++) { // open ten processes for ($j=0; $j<10; $j++) { $pipe[$j] = popen("script2.php", "w"); } // wait for them to finish for ($j=0; $j<10; ++$j) { pclose($pipe[$j]); } }

    Threading nav pieejams PHP krājumā, taču ir iespējama vienlaicīga programmēšana, izmantojot HTTP pieprasījumus asinhrono zvanu veidā.

    Ja locīšanas taimauta opcija ir iestatīta uz 1 un procesiem, kurus vēlaties saistīt viens ar otru, tiek izmantots tas pats session_id, varat saistīt sesijas mainīgos, kā manā piemērā tālāk. Izmantojot šo metodi, jūs pat varat aizvērt pārlūkprogrammu, un vienlaikus process joprojām pastāv serverī.

    Neaizmirstiet pārbaudīt pareizo sesijas ID, piemēram:

    http://localhost/test/verifysession.php? sessionid = [pareizais id]

    startprocess.php

    $request = "http://localhost/test/process1.php?sessionid=".$_REQUEST["PHPSESSID"]; $ch = curl_init(); curl_setopt($ch, CURLOPT_URL, $pieprasījums); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_TIMEOUT, 1); curl_exec($ch); curl_close($ch); echo $_REQUEST["PHPSESSID"];

    process1.php

    set_time_limit(0); if ($_REQUEST["sesijas ID"]) session_id($_REQUEST["sesijas ID"]); funkcija checkclose() ( globālā $_SESSION; if ($_SESSION["sesija"]) ( unset($_SESSION["closession"]); die(); ) ) while(!$close) ( session_start(); $_SESSION ["tests"] = rand(); checkclose(); session_write_close(); miegs(5); ) ar set_time_limit(0); if ($_REQUEST["sesijas ID"]) session_id($_REQUEST["sesijas ID"]); funkcija checkclose() ( globālā $_SESSION; if ($_SESSION["sesija"]) ( unset($_SESSION["closession"]); die(); ) ) while(!$close) ( session_start(); $_SESSION ["tests"] = rand(); checkclose(); session_write_close(); miegs(5); ) in set_time_limit(0); if ($_REQUEST["sesijas ID"]) session_id($_REQUEST["sesijas ID"]); funkcija checkclose() ( globālā $_SESSION; if ($_SESSION["sesija"]) ( unset($_SESSION["closession"]); die(); ) ) while(!$close) ( session_start(); $_SESSION ["tests"] = rand(); checkclose(); session_write_close(); miegs(5); )

    verifysession.php

    if ($_REQUEST["sesijas ID"]) session_id($_REQUEST["sesijas ID"]); session_start(); var_dump($_SESIJA);

    closeprocess.php

    if ($_REQUEST["sesijas ID"]) session_id($_REQUEST["sesijas ID"]); session_start(); $_SESSION["slēgšana"] = patiess; var_dump($_SESIJA);

    Lai gan jūs nevarat izveidot pavedienu, jums ir noteikta procesa kontroles pakāpe php. Šeit ir divi noderīgi komplekti:

    Procesu vadības funkcijas http://www.php.net/manual/en/ref.pcntl.php

    Varat izveidot savu procesu ar pcntl_fork — atgrieziet bērna PID. Pēc tam varat izmantot posix_kill, lai izmantotu šo PID.

    Tomēr, ja jūs nogalinat vecāku procesu, ir jānosūta signāls bērna procesam, liekot tam mirt. Ja php pats to neatpazīst, varat reģistrēt funkciju, lai to pārvaldītu, un veikt tīru izeju, izmantojot pcntl_signal.

    Jūs varat simulēt pavedienus. PHP var sākt fona procesus, izmantojot popen (vai proc_open). Šos procesus var vadīt, izmantojot stdin un stdout. Protams, šie procesi var būt php programma. Tas, iespējams, ir tik tuvu, cik iespējams.

    Varat izmantot exec(), lai palaistu komandrindas skriptu (piem., php komandrindu), un, ja ievadāt izvadi failā, skripts negaidīs, līdz komanda tiks pabeigta.

    Es neatceros CLI php sintaksi, bet jums ir nepieciešams kaut kas līdzīgs:

    Exec("/ceļš/uz/php -f "/ceļš/uz/failu.php" | "/ceļš/uz/output.txt"");

    Es domāju, ka dažiem dalītā mitināšanas serveriem drošības apsvērumu dēļ pēc noklusējuma ir atspējots exec (), taču tas varētu būt vērts mēģināt.

    Atkarībā no tā, ko mēģināt darīt, lai to sasniegtu, varat arī izmantot curl_multi.

    Tā atbalsta divvirzienu starppavedienu saziņu, kā arī tajā ir iebūvēta aizsardzība bērnu pavedienu iznīcināšanai (bāreņu profilakse).

    Jums var būt šāda iespēja:

    1. multi_curl
    2. Tam varat izmantot sistēmas komandu
    3. Ideāls scenārijs ir izveidot straumēšanas funkciju programmā C un kompilēt/konfigurēt PHP. Šī funkcija tagad būs PHP funkcija.

    Kā ar pcntl_fork?

    pārbaudiet piemērus mūsu man lapā: PHP pcntl_fork

    pcntl_fork nedarbosies tīmekļa servera vidē, ja tas ir iespējots drošais režīms. Šajā gadījumā tas darbosies tikai CLI PHP versijā.

    Pavedienu klase ir pieejama kopš PECL pthreads ≥ 2.0.0.