Bash: vylepšení efektivity funkce na uspořádání pole json

Už nějakou dobu jsem zkoušel používat ChatGPT k tomu aby mi uspořádal pole s knihami. Ovšem nějak se nedařilo, bylo to dost neefektivní.

První pole obsahuje seznam knih, správně seřazený (pole s klíči). Druhý seznam je datový, který obsahuje více informací a bohužel není seřazený podle názvu knih.

Chtěl jsem tedy po chatGPT aby načetl nejprve ten první soubor s klíči a podle toho pole pak seřadil to datové pole. Nejprve mi navrhl funkci, kde pole nebo soubor se načítá uvnitř. Taky byl problém, ten se nepovedlo vyřešit, že když klíč v datovém souboru či poli neexistoval, nevypsal se název pole. A to nešlo za nic na světě realizovat.

Tak jsem napsal samostatný kód, který nejprve porovná ty klíče, zda se nachází v datovém souboru nebo ne. Taky jsem se učil jak vlastně dostat celé pole do funkce, tak jsem to navrhl takto, že se soubor s klíči načte před funkcí sort_books. Pak ale stále ještě byl problém s efektivitou, že se snad 26 knih dlouho třídí. Asi 2.5s na mém AMD FX 8300 je dost dlouhá doba.

Asi není úplně ideální spouštět ten jq 26x ve smyčce a navíc se tam 26x načítá pole pomocí map. Máte někdo nějaký nápad jak to ještě urychlit a dostat ten čas například na 0.26 nebo 0.026 s?

PS:ChatGPT stále nechápe syntaxi jq... a vyvozuje nesprávné závěry.
Syntaxe datového souboru.json

Kód: [Vybrat]
{ "books": [{ "english_title": "nejaka kniha", "czech_title": "ceskynazev", "category": "beletrie", "chapter_count": 14 }, ...]}
Syntaxe klíčů:
[
  {"132153": {"no": 1, "title": "Nejaka kniha"}},
  {"456832": {"no": 2, "title": "Dalsi kniha"}},
...
]
« Poslední změna: 14. 06. 2023, 15:04:09 od Petr Krčmář »


alex6bbc

  • *****
  • 1 616
    • Zobrazit profil
    • E-mail
Re:Bash: Vylepšení efektivity funkce na uspořádání pole json.
« Odpověď #1 kdy: 14. 06. 2023, 14:29:37 »
* klice jsi serazoval jak, podle velikosti? :-)
* proc neserazujes knihy podle nazvu, podle autora apod.?
* neda se pouzit existujici priklad?

Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #2 kdy: 14. 06. 2023, 16:33:42 »
Má to svůj důvod proč ty knihy jsou přesně seřazené. Ale nechci sem přímo posílat data. Leda snad soukromě. Není to zas tak dlouhý json.

Karmelos

  • *****
  • 1 022
    • Zobrazit profil
    • E-mail
Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #3 kdy: 14. 06. 2023, 18:32:23 »
Proč bash? Těch 2.5 s se mi nezdá tolik, moje výpočty trvají o několik řádů dýl.
Nicméně, zamyslel bych se, proč to nenapsat rovnou v assembleru, mohlo by to bejt podle mě rychlejší.

..anebo ve vedlejším vlákně neví Stilgar do čeho píchnout v C++, tak třeba by se tomuhle moh' věnovat.
« Poslední změna: 14. 06. 2023, 18:34:25 od Karmelos »
Gréta je nejlepší.

z_sk

Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #4 kdy: 14. 06. 2023, 20:11:39 »
Súbor a:
Kód: [Vybrat]
{ "books": [

{ "english_title": "nejaka kniha", "czech_title": "ceskynazev", "category": "beletrie", "chapter_count": 14 },
{ "english_title": "Dalsi kniha", "czech_title": "ceskynazev", "category": "beletrie", "chapter_count": 14 },
{ "english_title": "aaa", "czech_title": "ceskynazev", "category": "beletrie", "chapter_count": 14 },
{ "english_title": "bbb", "czech_title": "ceskynazev", "category": "beletrie", "chapter_count": 14 },
{ "english_title": "ccccc", "czech_title": "ceskynazev", "category": "beletrie", "chapter_count": 14 }

]}

Súbor b:
Kód: [Vybrat]
[
  {"132153": {"no": 1, "title": "Nejaka kniha"}},
  {"456832": {"no": 2, "title": "Dalsi kniha"}},
  {"54654": {"no": 3, "title": "aaa"}},
  {"65648": {"no": 4, "title": "bbb"}},
  {"8787": {"no": 5, "title": "ccccc"}}
]

Kód (súbor a.php):
Kód: [Vybrat]
<?php

/*
 * Licence: CC0 
 * Licence URL: https://creativecommons.org/publicdomain/zero/1.0/legalcode
 * 
 * Run: php a.php
 */

function vypise_zoznam($path_book$path_keys)
{
$file=file_get_contents("$path_book");
$input_books=json_decode($filetrue);

$file=file_get_contents("$path_keys");
$keys=json_decode($filetrue);

//  books priradujem podla key
$books=array();
foreach($input_books['books'] as $book)
{
$new_key="X".$book['english_title'];

if(isset($books["$new_key"]))
{
// ak taky uz existuje
}

$books["$new_key"]=$book;
}

// vypis
foreach($keys as $key_item)
{
$key_id=array_key_first($key_item);
$key_data=$key_item[$key_id];

$real_title=$key_data['title'];

$key_check="X".$real_title;
if(isset($books["$key_check"]))
{
echo "$real_title - mame.\n";

$book=$books["$key_check"];
// print_r($book);
}
else
{
echo "$real_title - nemame.\n";
}
}
}
vypise_zoznam("a""b");


Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #5 kdy: 15. 06. 2023, 00:34:50 »
Nějak nevidím v druhém poli nějaký unikátní klíč. Jestli má být jeho klíčem a zároveň vazbou na první pole anglický název, tak je to dost nejistá a nespolehlivá vazba, knih s totožnými názvy jsou mraky.

Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #6 kdy: 15. 06. 2023, 02:00:21 »
Podle čeho se třídí je soubor s klíči. Jsou seřazeny. V tomto pořadí se mají třídit knihy v datovém souboru. Tzn. tady je to "title", který je tím rozhodujícím klíčem v datovém souboru. V datovém souboru je to "english_title". Funkce map(select ... má najít v datovém souboru ten správný klíč. Když ho najde, přičte se do pole a ukončí cyklus smyčky. Takto se vytváří nové pole s již seřazenými klíči.

Syntaxe klíčů:
[
  {"132153": {"no": 1, "title": "Nejaka kniha"}},
  {"456832": {"no": 2, "title": "Dalsi kniha"}},
...
]

alex6bbc

  • *****
  • 1 616
    • Zobrazit profil
    • E-mail
Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #7 kdy: 15. 06. 2023, 06:50:12 »
a nechapu kde je problem?

pole s klici je serazene tak jen v hlavnim cyklu projizdim prvky.
ve vnitrnim cyklu projizdim seznam knih, kdyz pasuje nazev ze seznamu s klici s nazvem ze seznamu knih, tak knihu vypisu.

jak to zrychlit? odstranovat pouzite zaznamy z obou seznamu.

Re:Bash: vylepšení efektivity funkce na uspořádání pole json
« Odpověď #8 kdy: 15. 06. 2023, 09:47:51 »
Bash umí asociativní pole. Takže stačí jedním spuštěním jq načíst "datový soubor" do asociativního pole (kde klíčem bude english_title a hodnotou ostatní data) a pak druhým spuštěním jq načíst "soubor s klíči" a v cyklu přes všechny klíče se podívat do toho asociativního pole a vypsat jeho hodnoty. I pro tisíce knih to bude trvat zlomek vteřiny.

Pokud není english_title unikátní, tak se to musí ohlídat a při načítání datového souboru ty hodnoty v asociativním poli přidávat (a nikoli jen přepisovat).
« Poslední změna: 15. 06. 2023, 09:53:34 od kouli »