Pchełki SQL, odcinek 8: dekropkizacja subiektyzacji

Dzisiejszy odcinek pchełek SQL będzie poświęcony zagadnieniu usuwania kropek z końców tytułów wpisów na blogu WordPress.

Od razu zaznaczam, że - ponieważ nie jestem fachowcem od MySQL - pchełka dzisiejsza pokaże rozwiązanie, które owszem, działa, ale jest dalekie od idealnego. Łamie też prawdopodobnie większość zasad poprawnego programowania, a więc proszę tego nie stosować w środowisku produkcyjnym, testowym, developerskim... w zasadzie to proszę w ogóle nie czytać tego wpisu. Grozi awarią.

Jednak czytasz dalej?

No dobra...

Zasadniczo problem polega na tym, że ktoś kiedyś (prawdopodobnie jeszcze w szkole podstawowej) wpoił mi zasadę interpunkcji mówiącą, że na końcu zdania stawia się kropkę. Niestety, nikt mi potem nigdy nie uświadomił, że od tej reguły są wyjątki. Na przykład - tytuły. W tytułach książek, opowiadań, wpisów na blogu... No, w tytułach, nie stawia się kropek na końcu zdania, o ile tytuł jest jednozdaniowy.

No a ja, nie wiedząc o tym, dzielnie wstawiałem kropki na końcu wszystkich tytułów - w każdym razie tych, które nie kończą się znakiem zapytania albo wykrzyknikiem (aczkolwiek, jak zauważył niedawno Pendragon, znak zapytania też ma kropkę, a więc technicznie rzecz biorąc jest to kropka na końcu zdania).

No i - ku memu niekłamanemu przerażeniu - Przemek uświadomił mnie niedawno, że to jest błąd, że kropek ma nie być. Tzn. nie ma być.

Najpierw złapałem się za głowę...

Nie, wróć, najpierw sprawdziłem internetowe zasoby wiedzy gramatycznej, i faktycznie, o zgrozo, kropki się nie stawia na końcu tytułu.

Potem się złapałem za głowę. Dobrze ponad pół tysiąca wpisów, statystycznie rzecz biorąc przynajmniej połowa z nich ma kropkę na końcu. Co robić, panie premierze, co robić?

Ale zaraz potem sobie myślę tak: przecież taki blog to nic innego jak baza danych ujeżdżana przez Apacza, prawda? A skoro baza danych, to SQL. A skoro SQL, to musi się dać te kropki jakoś automagicznie wyrezać, nie ma bata.

No więc siadłem do klawiatury i dalejże:

select *
from wp_posts;

Aha, patrzę, jest kolumna post_title. No to od razu:

select *
from wp_posts
where right(post_title, 1) = '.';

Bang, działa, dostałem wszystkie posty, których tytuły kończą się kropką. A czasem nawet trzema. Myślę, trzykropkom nie będziemy kropek amputować, a więc mała korekta:

select *
from wp_posts
where right(post_title, 1) = '.'
    and right(post_title, 2) <> '..';

W wyniku dostałem ciut ponad dwieście postów. Teraz tylko trzeba by te kropki amputować i po kłopocie, prawda?

Na wszelki wypadek, zanim zapuściłem amputację właściwą, postanowiłem sprawdzić jak wyglądać będą te odkropkowane tytuły:

select post_title, 
    left(post_title, len(post_title)-1) new_pt
from wp_posts 
where right(post_title, 1) = '.' 
    and right(post_title, 2) <> '..';

I co? I gówno kupa, nie działa. A raczej działa częściowo: w niektórych tytułach kropki na końcu nie ma, a w innych jest, jakby nigdy nic. Pomyślałem sobie, że może tam spacje są na końcu, ale nie, nie było.

Przyjrzałem się raz jeszcze i zauważyłem, że kropki zniknęły z tytułów, które nie zawierają polskich znaków. A tam, gdzie jest jakieś ę czy ó, kropka zostaje jakby nigdy nic.

Myślę sobie wtedy, pewnie coś z UTF czy innym kodowaniem. Sprawa zaczynała mi już lekko śmierdzieć, ponieważ nie chciało mi się już zagłębiać w zagadnienie kodowania znaków w MySQL. Wziąłem się więc na sposób. Pomyślałem, że skoro kropka jest na końcu, to jak odwrócę tekst (za przeproszeniem, "od tyłu"), to kropka będzie na początku, prawda? A łatwiej usunąć kropkę z początku tekstu niż z końca, bo jak jest na początku, znamy dokładnie jej pozycję w tekście.

No i wykluło się takie coś:

select post_title, 
    reverse(substring(reverse(post_title), 2, 1000)) as new_pt
from wp_posts 
where right(post_title, 1) = '.' 
    and right(post_title, 2) <> '..';

Tym razem zadziałało bez pudła i oto na ekranie pokazała się lista tytułów bez kropek na końcu.

Pozostało jeszcze tylko wykonać amputację właściwą:

update wp_posts
set wp_title = reverse(substring(reverse(post_title), 2, 1000))
where right(post_title, 1) = '.' 
    and right(post_title, 2) <> '..';

Zanim to zapuściłem, na wszelki wypadek skopiowałem tabelę wp_posts "na bok", w razie jakby trzeba było ją awaryjnie odtwarzać. Ale nie trzeba było. Kropek nie ma, jakby nigdy nie istniały...

4 komentarze

  1. Jak się zna eskuel, to się szybko takie rzeczy załatwia. Ja musiałbym to robić na piechotę 🙂

    Jak już jestem w temacie, to tą twoją słitaśną kapczę nie da rady obsłużyć na smartfonie. Albo ja nie umiem?

    1. Sweet Captcha deklarują, że są zgodni z Androidem i IOS-em. Niestety, mi na Androidzie też nie działa i póki co nie wiem jak to obejść.

      1. Zgodność z Androidem jest: Sweet Captcha i Android zgadzają się, że nie działa.

        A co do tej perełki to może uda mi się coś z tego wykorzystać w brutalnych celach (czyt.: w terroryzowaniu studentów).

        1. Oj ja bym się do tego kodu przed studentami nie przyznawał. Takie dwukrotne odwracanie stringów do niczego dobrego nie prowadzi (jakkolwiek dwuznacznie by się to nie kojarzyło).

Leave a Comment

Komentarze mile widziane.

Jeżeli chcesz do komentarza wstawić kod, użyj składni:
[code]
tutaj wstaw swój kod
[/code]