Przeszukiwanie ciągu znaków według kilku podciągów

0

Witam, potrzebuję przeszukać elementy tablicy które są stringami względem kilku podciągów takimi jak: cena, kolor-, bestseller, prezenty itd. Jeśli ciąg NIE zawiera takiego podciągu to ma być wyświetlony. Próbowałam stworzyć tablicę z takimi podciągami i względem niej przeszukiwać w instrukcji warunkowej, jak również funkcji in_array(), preg_match(), strpos() ale bez powodzenia przy większej ilości kryteriów. Czy jest jakiś sposób by sprawdzić ciąg pod kątem kilku różnych podciągów ?
Dziękuję za wszelką pomoc.

1

pokaz jak wyglada tablica

3

Najprościej byłoby chyba użyć preg_match

<?php
$match = "super cena";
$no_match = " super zabawka";
$patterns = ['cena','kolor'];
$master_pattern = "'" . implode($patterns, "|") . "'";// | to or w regex

var_dump(preg_match($master_pattern , $match));
var_dump(preg_match($master_pattern , $no_match));
?>
0
jurek1980 napisał(a):

Najprościej byłoby chyba użyć preg_match

<?php
$match = "super cena";
$no_match = " super zabawka";
$patterns = ['cena','kolor'];
$master_pattern = "'" . implode($patterns, "|") . "'";// | to or w regex

Nie łącz tak patternów, lepiej zrobić Pattern::alteration($patterns).

0

@masterc: Przykładowa tablica wygląda tak:
Array (
[0] => string1
[1] => string2
[2] => string3
itd.
)
Stringami są właściwości produktu.

@jurek1980: Ok, spróbuję.
@TomRiddle: Chcę tylko wyświetlić elementy z tablicy które tych słów nie zawierają, bez usuwania ich z tablicy. Sprawdzę zaproponowane rozwiązania

1
kasia13130 napisał(a):

@TomRiddle: Chcę tylko wyświetlić elementy z tablicy które tych słów nie zawierają, bez usuwania ich z tablicy. Sprawdzę zaproponowane rozwiązania

No ale przecież w moim przykładzie nie modyfikujesz swojej tablicy, tylko tworzysz nową bez tych elementów. W moim przykładzie $inputArray to jest Twój wejściowa tablica, a $result to jest wynik, z tymi elementami które chcesz.

PS: Okej, może źle się wyraziłem z "usunięciem z tablicy". Posłużyłem się takim skrótem, bo w profesjonalnych projektach właściwie unika się modyfikowania stanu (operacji na tablicach bezpośrednio), więc uznałem za oczywistę że nie będziemy modyfikować istniejącej tablicy, tylko stworzymy nową.

0

@TomRiddle: Tak, widzę. Odpowiedziałam tylko na Twoje pytanie które zadałeś na samym początku swojego postu by nie było wątpliwości.

0
kasia13130 napisał(a):

@masterc: Przykładowa tablica wygląda tak:

Array (
[0] => string1
[1] => string2
[2] => string3
itd.
)
Stringami są właściwości produktu.

niemozwliwe zeby tak wygladala tablica, po pierwsze nie widac tu nazwy produktu, a po drugie kluczem powinna byc

[cena] => 340

a tak to co jest

[0] => 'cena: 120'
0
kasia13130 napisał(a):

@TomRiddle: Tak, widzę. Odpowiedziałam tylko na Twoje pytanie które zadałeś na samym początku swojego postu by nie było wątpliwości.

Udało Ci się rozwiązać problem?

0

@TomRiddle: Częściowo tak, jeszcze próbuję wyfiltrować takie elementy jak np. marka-nazwaMarkigramatura-sztuka. Mam kilka tego typu elementów w tablicy, a potrzebuję zostawić tylko elementy typu marka-nazwaMarki oraz takie elementy jak kolor- (bez wartości koloru) które również potrzebuję wyfiltrować tak by zostały te które mają po '-' określony kolor.

P.S. przy filtrowaniu elementów marka muszę zrobić takie zastawienie by tylko w połączeniu marki z gramatura-sztuka elementy nie były wyświetlane, natomiast gdy są osobno to mają być wyświetlone (to jest bardziej kłopotliwe)

0
kasia13130 napisał(a):

@TomRiddle: Częściowo tak, jeszcze próbuję wyfiltrować takie elementy jak np. marka-nazwaMarkigramatura-sztuka. Mam kilka tego typu elementów w tablicy, a potrzebuję zostawić tylko elementy typu marka-nazwaMarki oraz takie elementy jak kolor- (bez wartości koloru) które również potrzebuję wyfiltrować tak by zostały te które mają po '-' określony kolor.

Strasznie to zagmatwanie przedstawiłeś.

Skąd w ogóle bierzesz tą tablice?

0

@TomRiddle: Otrzymałam taką tablicę by na jej podstawie wykonać zadanie.

0

W innych postach pisałaś o pobraniu danych z bazy.
Może wrzuć opis tabeli. Może wszystko można ogarnąć już na poziomie SQL?

0
kasia13130 napisał(a):

@TomRiddle: jeszcze próbuję wyfiltrować takie elementy jak np. marka-nazwaMarkigramatura-sztuka. Mam kilka tego typu elementów w tablicy, a potrzebuję zostawić tylko elementy typu marka-nazwaMarki oraz takie elementy jak kolor- (bez wartości koloru) które również potrzebuję wyfiltrować tak by zostały te które mają po '-' określony kolor.

P.S. przy filtrowaniu elementów marka muszę zrobić takie zastawienie by tylko w połączeniu marki z gramatura-sztuka elementy nie były wyświetlane, natomiast gdy są osobno to mają być wyświetlone (to jest bardziej kłopotliwe)

kasia13130 napisał(a):

@TomRiddle: Otrzymałam taką tablicę by na jej podstawie wykonać zadanie.

Strasznie to wszystko jest zagmatwane, i tak na prawdę ciężko się domyślić co robisz. Z tego co ja rozumiem, to mając taki array

[
  'nokia-kg-2',
  'nokia-m-3-blue'
]

Chcesz wyświetlić to na dwa sposoby, raz tak:

['blue']

a raz tak

['kg', 'm']

Dobrze rozumiem?

Najlepiej byłoby jakbyś dała przykład danej wejściowej, oraz to jak chciałbyś je wyświetlić.

0

@TomRiddle: Może tak będzie łatwiej, dla przykładowej tablicy.
Array (
[0] => cena-100
[1] => rodzaj-kryminal
[2] => rodzaj-dramat
[3] => okladka-miekka
[4] => okladka-twarda
[5] => autor-JanKowalski
[6] => autor-JanKowalskicena-100
[7] => autor-JanKowalskicena-100cena-100
[8] => autor-MagdaKowalska
[9] => autor-MagdaKowalskarodzaj-kryminal
[10] => wydawnictwo-NowaEra
[11] => wydawnictwo-NowaEraokladka-twarda
[12] => wydawnictwo-NowaEraokladka-twardaokladka-twarda
[13] => wydawnictwo-Helion
)

Chcę uzyskać:
rodzaj-kryminal
rodzaj-dramat
okladka-miekka
okladka-twarda
autor-JanKowalski
autor-MagdaKowalska
wydawnictwo-NowaEra
wydawnictwo-Helion

Tablicy na której pracuję niestety nie mogę udostępnić. Dopiero PHP się uczę dlatego muszę to zaimplementować.

1
kasia13130 napisał(a):

@TomRiddle: Może tak będzie łatwiej, dla przykładowej tablicy.

Array (
[0] => cena-100
[1] => rodzaj-kryminal
[2] => rodzaj-dramat
[3] => okladka-miekka
[4] => okladka-twarda
[5] => autor-JanKowalski
[6] => autor-JanKowalskicena-100
[7] => autor-JanKowalskicena-100cena-100
[8] => autor-MagdaKowalska
[9] => autor-MagdaKowalskarodzaj-kryminal
[10] => wydawnictwo-NowaEra
[11] => wydawnictwo-NowaEraokladka-twarda
[12] => wydawnictwo-NowaEraokladka-twardaokladka-twarda
[13] => wydawnictwo-Helion
)

Chcę uzyskać:
rodzaj-kryminal
rodzaj-dramat
okladka-miekka
okladka-twarda
autor-JanKowalski
autor-MagdaKowalska
wydawnictwo-NowaEra
wydawnictwo-Helion

Tablicy na której pracuję niestety nie mogę udostępnić. Dopiero PHP się uczę dlatego muszę to zaimplementować.

No dobra, powiedzmy że coś mamy.

No to pierwsze pytanie, czy te dane muszą być w takiej formie? Bo tutaj są posklejane frazy, ciężko będzie zrobić coś sensownego z tym. Dla przykładu - co jeśli ktoś ma słowo "cena" lub "rodzaj" w imieniu, nazwisku lub nazwie marki? wydawnictwo-MamyUrodzajcena-100. rodzaj ze słowa "Urodzaj" będzie potraktowany jako słowo kluczowe. Gdyby tam chociaż były jakieś separatory, przecinki lub coś innego, można by myśleć jak to ogarnąć. Gdyby to w ogóle były osobne struktury to byłoby najlepiej. Dodatkowo, tutaj specjalnym znakiem jest myślnik -, co jeśli ktoś ma myślink w nazwisku? Nie będzie tego można jednoznacznie stwierdzić.

Dlatego ja bym się mocno zastanowił skąd te dane pochodzą, i czy nie da się ich dostać w jakiejś lepszej formie.

0

@TomRiddle: Tak, musi być w takiej formie. Właśnie w tym problem, dlatego napisałam na forum by jakoś się z tym uporać.

1
kasia13130 napisał(a):

@TomRiddle: Tak, musi być w takiej formie. Właśnie w tym problem, dlatego napisałam na forum by jakoś się z tym uporać.

No to odpowiedź jednoznaczna jest taka, że w takiej formie w jakiej to jest teraz przedstawione, to nie da się jednoznacznie przedstawić tych dwóch pozycji. Są nazwiska które mają myślniki, Więc Mógłby być taki autor jak Magda Kowalskarodzaj-kryminał. To byłoby całkowicie normalne polskie nazwisko. Jeśli taka osoba znajdzie się w Twojej tablicy, i zobaczysz

[9] => autor-MagdaKowalskarodzaj-kryminal

to (zostając przy takim zapisie) nie jesteś w stanie stwierdzić czy to jest autor - "Magda Kowalskarodzaj-kryminał", czy autor - "Magda Kowalska", rodzaj - "kryminał".

Twoim jedynym wyjściem jest po prostu założyć, tak, założyć, że nie ma wartości w Twojej tablicy które odpowiadają słowom kluczowym. Żeby dopuścić takie nazwiska (i w ogóle wartości), musiałabyś dodać jakiś separator.

Drugim problemem jest to, czy dane faktycznie są poprawne. Np czy może się pojawić tekst rodzaj-cena-100? Co wtedy się powinno stać?

Ale okej, zakładając że wartości i słowa kluczowe się nienachodzą (niebezpieczne założenie, jeśli mnie pytasz). To to, co ja zrobiłbym na początku to jest zamieniłbym tą dziwną array, na sensowną array. Czyli pierwszy krok to jest rozparsowanie jej.

Czyli musisz zmienić taką tablicę:

Array (
[6] => autor-JanKowalskicena-100
[7] => autor-JanKowalskicena-100cena-100
[8] => autor-MagdaKowalska
[9] => autor-MagdaKowalskarodzaj-kryminal
[10] => wydawnictwo-NowaEra
[11] => wydawnictwo-NowaEraokladka-twarda
[12] => wydawnictwo-NowaEraokladka-twardaokladka-twarda
[13] => wydawnictwo-Helion
)

na taką

Array (
[6] => [autor => 'JanKowalski', cena => 100]
[7] => [autor => 'JanKowalski', cena => 100]
[8] => [autor => 'MagdaKowalska']
[9] => [autor => 'MagdaKowalska', rodzaj => 'kryminal']
[10] => [wydawnictwo => 'NowaEra']
[11] => [wydawnictwo => 'NowaEra', okladka => 'twarda']
[12] => [wydawnictwo => 'NowaEra', okladka => 'twarda']
[13] => [wydawnictwo => 'Helion']
)

żeby to osiągnąć, możesz na każdym elemencie list zrobić splita po słowach kluczowych.

Ja to zrobiłem takim kodem:

$keywordsArray = [];
foreach ($inputArray as $string) {
    $split = \preg_split('/(cena|rodzaj|okladka|autor|wydawnictwo)-/', $string, -1, \PREG_SPLIT_DELIM_CAPTURE);
    $keywordsArray[] = \array_slice($split, 1);
}

i uzyskałem taką tablicę.

array(14) {
  [0] =>
  array(2) {
    [0] =>
    string(4) "cena"
    [1] =>
    string(3) "100"
  }
  // ...
  [9] =>
  array(4) {
    [0] =>
    string(5) "autor"
    [1] =>
    string(13) "MagdaKowalska"
    [2] =>
    string(6) "rodzaj"
    [3] =>
    string(8) "kryminal"
  }
  [10] =>
  array(2) {
    [0] =>
    string(11) "wydawnictwo"
    [1] =>
    string(7) "NowaEra"
  }
  [11] =>
  array(4) {
    [0] =>
    string(11) "wydawnictwo"
    [1] =>
    string(7) "NowaEra"
    [2] =>
    string(7) "okladka"
    [3] =>
    string(6) "twarda"
  }
  [12] =>
  array(6) {
    [0] =>
    string(11) "wydawnictwo"
    [1] =>
    string(7) "NowaEra"
    [2] =>
    string(7) "okladka"
    [3] =>
    string(6) "twarda"
    [4] =>
    string(7) "okladka"
    [5] =>
    string(6) "twarda"
  }
  [13] =>
  array(2) {
    [0] =>
    string(11) "wydawnictwo"
    [1] =>
    string(6) "Helion"
  }
}

Teraz, dla każdego elementu, trzeba wziąć co drugi kluczi i co drugą wartośc, i połączyć ja w jedną entry klucz => wartość. Ja to zrobiłem w taki sposób:

function parseString(string $string): array {
    $chunks = \array_chunk(splitString($string), 2);
    $result = [];
    foreach ($chunks as [$key, $value]) {
        $result[$key] = $value;
    }
    return $result;
}

function splitString(string $string) {
    $split = \preg_split('/(cena|rodzaj|okladka|autor|wydawnictwo)-/', $string, -1, \PREG_SPLIT_DELIM_CAPTURE);
    return \array_slice($split, 1);
}

$inputArray = [
    // ... Twoje dane
];

$keywordsArray = [];
foreach ($inputArray as $string) {
    $keywordsArray[] = parseString($string);
}
var_dump($keywordsArray);

Uzyskałem wtedy

  [9] =>
  array(2) {
    'autor' =>
    string(13) "MagdaKowalska"
    'rodzaj' =>
    string(8) "kryminal"
  }
  [10] =>
  array(1) {
    'wydawnictwo' =>
    string(7) "NowaEra"
  }
  [11] =>
  array(2) {
    'wydawnictwo' =>
    string(7) "NowaEra"
    'okladka' =>
    string(6) "twarda"
  }
  [12] =>
  array(2) {
    'wydawnictwo' =>
    string(7) "NowaEra"
    'okladka' =>
    string(6) "twarda"
  }
  [13] =>
  array(1) {
    'wydawnictwo' =>
    string(6) "Helion"
  }
}

screenshot-20210923144339.png

1

Mając funkcję parseString, możemy przelecieć po Twojej całej tablicy, i sparsować te dane. Oczywiście nazwiska która mają w sobie cena, rodzaj zostaną niepoprawnie rozpoznane.

Teraz, mając tak poprawnie przygotowaną tablicę, możemy przejść do faktycznego wyświetlania Twoich danych. I teraz rozumiem, że np chcesz zostawić tylko te która mają cenę 100?

No to robisz tak

$result = [];
foreach ($inputArray as $weirdString) {
  $goodArray = parseString($weirdString);
  if ($goodArray['cena'] == '100') // Twoje filtrowanie
  {
    $result[] = $goodArray;
  }
}

I teraz $result możesz normalnie wyświetlić ;)

0

Kaśka weź im powiedz zeby sobie wsadzili to zadanie w d.... bo to co masz to jest g.... a nie dane wejsciowe. wystarczy ze ktos zapomni dodac ceny czy typ okładki i np masz wydawnictwo-NowaEraokladka-okladka-twarda i już cały miesterny plan nie powiem gdzie. Nie dośc że się uczysz to już ci każa robić złe nawyki.

0

@TomRiddle: Bardzo dziękuję za pomoc :)

1 użytkowników online, w tym zalogowanych: 0, gości: 1