AKTUALIZACJA: Moje oryginalne pytanie zostało rozwiązane, ale zamienia się w ważną dyskusję na temat tego, dlaczego nie używać zmiennych globalnych, dlatego aktualizuję pytanie, aby to odzwierciedlić. Rozwiązanie było takie, <?php global $category_link_prop; echo esc_url( $category_link_prop ); ?>
jak sugerował @TomJNowell.
AKTUALIZACJA 2: Teraz robię dokładnie to, co chciałem. Ale nadal używam globalnego zasięgu i chętnie znajdę lepszy sposób.
Próbuję skonfigurować całą masę zmiennych globalnych dla bezpośrednich łączy do kategorii, które będą używane w różnych miejscach mojego motywu. Głównym tego powodem jest użycie zarówno w głównej nawigacji, jak i w szeregu nawigacji podrzędnych, które są wybierane na podstawie kategorii, w której znajduje się bieżący post. To nie jest temat, który udostępnię innym osobom, ale został zbudowany w jednym, bardzo określonym celu.
Tak właśnie je teraz tworzę (wkleiłem tylko kilka zmiennych).
function set_global_nav_var()
{
//proposal
global $prop;
// Get the ID of a given category
$category_id_prop = get_cat_ID( 'proposal' );
// Get the URL of this category
$category_link_prop = get_category_link( $category_id_prop );
$prop = '<a href="' .esc_url( $category_link_prop ). '" title="Proposal">Proposal</a>';
//Calvinball
global $cb;
// Get the ID of a given category
$category_id_cb = get_cat_ID( 'calvinball' );
// Get the URL of this category
$category_link_cb = get_category_link( $category_id_cb );
$cb = '<a href="' .esc_url( $category_link_cb). '" title="Calvinball">Calvinball</a>';
}
add_action( 'init', 'set_global_nav_var' );
Mogę teraz zrobić <?php global $prop; echo $prop; ?>
4 miejsca i odzyskać cały link do kodu. Kiedy te zmiany muszę zmienić tylko w jednym miejscu. Jestem otwarty na alternatywy, które nie obejmują zasięgu globalnego.
Odpowiedzi:
Chociaż zdecydowanie odradzam to i nie przyspieszy to, twoje użycie jest nieprawidłowe.
Kiedy próbujesz użyć globalnego, musisz najpierw określić globalne słowo kluczowe. Podano go tutaj podczas definiowania jego wartości, ale poza tym zakresem należy go ponownie zadeklarować jako globalną zmienną zakresu.
np. w functions.php:
W single.php to nie zadziała:
Ponieważ $ hello jest niezdefiniowana. To jednak będzie działać:
Oczywiście nie powinieneś tego robić. WordPress już próbuje buforować te rzeczy w pamięci podręcznej obiektów. Dzięki temu nie zobaczysz żadnego wzrostu prędkości (możesz zauważyć niewielki spadek prędkości), wszystko co dostaniesz to dodatkowa złożoność i potrzeba wpisania wielu globalnych deklaracji, które nie są konieczne.
Lepiej byłoby użyć danych strukturalnych, takich jak wstrzyknięcie obiektów lub zależności, lub w twoim przypadku zestaw funkcji.
Na przykład, tutaj jest sposób na zrobienie czegoś podobnego za pomocą zmiennych statycznych (nadal złe z tych samych powodów, ale tylko trochę mniej i łatwiejsze do wpisania) np.
Jeśli naprawdę chcesz zaoszczędzić czas, przechowując dane w celu ponownego użycia, rozważ użycie
WP_Cache
systemu zwp_cache_get
itpźródło
<?php global $category_link_prop; echo esc_url( $category_link_prop ); ?>
zgodnie z twoją sugestią. Dzięki!Nie używaj zmiennych globalnych , tak proste.
Dlaczego nie korzystać z globałów
Ponieważ użycie globałów utrudnia utrzymanie oprogramowania w dłuższej perspektywie.
Rdzeń WordPress w znacznym stopniu wykorzystuje globały. Próbując zrozumieć, jak działają podstawowe funkcje
the_content
, nagle zdajesz sobie sprawę, że$more
zmienna nie jest lokalna, ale globalna i musisz przeszukać całe podstawowe pliki, aby zrozumieć, kiedy jest ustawiona na wartość true.Co więc można zrobić, gdy próbujesz zatrzymać kopiowanie i wklejanie kilku wierszy kodu zamiast przechowywać wynik pierwszego uruchomienia w globalnym? Istnieje kilka podejść, funkcjonalnych i OOP.
Funkcja słodzika. Jest to po prostu opakowanie / makro do zapisywania kopii / wklejania
Korzyści są takie, że teraz jest dokumentacja tego, co robi poprzedni globalny, i masz oczywisty punkt do debugowania, gdy zwracana wartość nie jest tą, której się spodziewasz.
Po otrzymaniu słodzika łatwo jest buforować wynik w razie potrzeby (zrób to tylko wtedy, gdy odkryjesz, że wykonanie tej funkcji zajmuje dużo czasu)
Daje to takie samo zachowanie globalne, ale ma tę zaletę, że zapewnia bezpieczną inicjalizację za każdym razem, gdy się do niego uzyskujesz.
Możesz mieć podobne wzorce z OOP. Uważam, że OOP zwykle nie dodaje żadnej wartości do wtyczek i motywów, ale to inna dyskusja
Jest to nieporadny kod, ale jeśli masz kilka wartości, które chcesz wstępnie obliczyć, ponieważ są one zawsze używane, może to być dobry sposób. Zasadniczo jest to obiekt, który zawiera wszystkie twoje globale w zorganizowany sposób. Aby uniknąć przekształcenia instancji tego obiektu w globalną (chcesz tylko jedną instancję, w przeciwnym razie przeliczasz wartości), możesz użyć wzorca singletonu (niektórzy twierdzą, że to zły pomysł, YMMV)
Nie lubię bezpośrednio uzyskiwać dostępu do atrybutu obiektu, więc w moim kodzie będzie to więcej
źródło
Twoje pytanie dotyczy działania php.
Weź jako przykład $ wpdb
$ wpdb jest znaną zmienną globalną.
Czy wiesz, kiedy zostanie zadeklarowany i przypisany wartościom?
Każda strona ładowana , tak, za każdym razem, gdy odwiedzasz witrynę Wordpress.
Podobnie musisz upewnić się, że zmienne, które chcesz zglobalizować, zostaną zadeklarowane i przyporządkowane do nich odpowiednie wartości przy każdej załadowanej stronie.
Chociaż nie jestem projektantem motywów, mogę powiedzieć, że after_setup_theme to jednorazowy haczyk. zostanie aktywowany tylko po aktywowaniu motywu.
Gdybym był tobą, użyłbym init lub innych haków. Nie, gdybym był tobą, w ogóle nie używałbym zmiennych globalnych ...
Naprawdę nie jestem dobry w wyjaśnianiu rzeczy. Powinieneś więc wybrać książkę, jeśli chcesz zagłębić się w PHP.
źródło
Zawsze możesz użyć wzorca singletonu za pomocą statycznych mechanizmów pobierających.
źródło