Dlaczego elisp nie ma przestrzeni nazw?

40

P: Dlaczego elisp nie ma przestrzeni nazw i jak możemy je zdobyć?

Elisp nie ma przestrzeni nazw innych niż globalna, co doprowadziło do konwencji kodowania polegającej na prefiksowaniu wszystkich globalnych funkcji, zmiennych i stałych unikalnym prefiksem.

Oprócz czynnika irytacji, wydaje mi się to również kwestią duszenia się, biorąc pod uwagę 1) stale rosnącą liczbę wielkich bibliotek i pakietów oraz 2) ciągłe istnienie starszych funkcji i zmiennych, które albo nie przestrzegają konwencji przedrostka, albo są wystarczająco idiosynkratyczni, że tak naprawdę nie ma dobrej opcji przedrostka, której mogliby użyć. Oznacza to również, że okresowe próby zracjonalizowania starszego kodu (jak w przypadku przejścia z clna cl-lib) są nietrywialnym nakładem pracy. (Chociaż cieszę się z tego sprzątania, wciąż ronię łzę za każdym razem, gdy piszę coś takiego cl-find).

Zacząłem się rozglądać, aby sprawdzić, czy po kilkudziesięciu latach użytkowania elisp nadal nie ma przestrzeni nazw, ale byłem trochę zaskoczony skromnymi zbiorami. Strona wiki w przestrzeniach nazw jest dość krótka. Nic Ferrier ma nieco dłuższe podejście do problemu, a także na temat emacs-devel . Istnieje stary wątek Przepełnienie stosu z 2010 roku, który omawia możliwość użycia makr do implementacji przestrzeni nazw; inny przykład podejścia makro można znaleźć tutaj . Istnieje co najmniej kilka implementacji ( tu i tutaj , wraz z opisem tych ostatnich tutaj), ale od kilku lat nie widzieli dużej aktywności i nie natknąłem się na biblioteki, które ich używają.

Zakładam, że gdyby dodanie przestrzeni nazw było łatwe, byłoby to już zrobione. Więc:

  • Jakie są techniczne przeszkody w dodawaniu przestrzeni nazw do elisp?
  • Czy dodanie przestrzeni nazw złamałoby wiele istniejących kodów?
  • Czy ta funkcjonalność musi być organiczna, by ją wywołać (zmiany w samym interpreterie), czy może naprawdę można ją zbudować za pomocą makr?
Dan
źródło
6
Możesz na to spojrzeć: github.com/Bruce-Connor/names Wydaje się, że jest to implementacja automatycznych przestrzeni nazw (z obecnym ręcznym sposobem oddzielania nazw). (I jestem 99% pewien, że widziałem inną taką bibliotekę, pozwalającą programistom wyeksportować podzbiór funkcji z przestrzeniami nazw, wspomniany ostatnio na blogu emacs, ale nie mogłem go znaleźć).
T. Verron
2
Po drugie, powinieneś spojrzeć na powyższy link. Jest to bardzo nowe (wydane w zeszłym miesiącu) i bardzo solidne makro przestrzeni nazw. Nadal pracuję nad kilkoma niezręcznościami w zakresie kompatybilności z narzędziami takimi jak edebug, ale pakiet działa. Odpowiedź na twoje pytanie to naprawdę długi esej (bariery techniczne, z którymi miałem do czynienia, było wiele), ale postaram się zamieścić je w postach na blogu w ciągu najbliższych tygodni.
Malabarba
1
Sądzę, że przestrzenie nazw oznaczają różne rzeczy. Powiedziałbym, że emacs ma kilka przestrzeni nazw: jedna dla zmiennych, druga dla funkcji i makr, druga dla twarzy i tematów i…
Harald Hanche-Olsen
1
@ HaraldHanche-Olsen z pewnością możesz to powiedzieć. W tym kontekście pyta, dlaczego nie ma przestrzeni nazw dla poszczególnych pakietów.
Malabarba

Odpowiedzi:

28

Dlaczego nie ma przestrzeni nazw?

Ponieważ jest to skomplikowane i nikt jeszcze nie uważał, że jest to wystarczająco pilne, aby w pełni się zanurzyć. Zostało to omówione wcześniej na liście deweloperów (więcej niż jeden raz) i pojawiły się obietnice rozwiązania tego po przejściu na git.

W międzyczasie napisałem własne rozwiązanie (lista opcji poniżej).

Jakie są bariery techniczne?

Tuż za drzwiami masz 3 duże przeszkody, które musisz pokonać, aby przestrzenie nazw miały nawet szansę pracować na obecnym Emacsie:

  • Musisz zmienić sposób internowania symboli (jest to łatwa część).
  • Kompilator bajtów musi zrozumieć przestrzenie nazw.
  • Generowanie automatycznego ładowania używane przez package.elmusi zrozumieć przestrzenie nazw.

Łagodzenie tych 3 rzeczy do pracy, jednak przy wdrażaniu przestrzeni nazw nie jest trywialne. Jeśli jesteś poświęcony tylko najnowszej wersji Emacsa, jest to z pewnością wykonalne. Jeśli chcesz napisać jakiś pakiet, który obsługuje również poprzednie wersje (jak cała rodzina 24), staje się to piekło wyzwaniem.

Poza tym istnieje mnóstwo innych opcjonalnych przeszkód. Elisp jest świetny ze względu na całą moc dostępnych narzędzi i WSZYSTKIE z nich musiałyby zostać załatane do pracy z przestrzeniami nazw. Do najważniejszych należą:

  • Edebug
  • eval-defun
  • eval-last-sexp
  • szlam

Czy złamałoby to wiele istniejących kodów?

Nie, jeśli zrobisz to dobrze.

Czy to coś, co musi być ekologiczne, czy też może być naprawdę zbudowane na makrach?

Idealnie byłoby organiczne, o tym zwykle dyskutuje się, gdy pojawia się na liście deweloperów. Ale może być wystarczająco dobry, gdy jest budowany na górze.
Oto kilka przykładów tego wziętych z tej listy :

Malabarba
źródło
1
Dzięki - to było bardzo pouczające spojrzenie na ten problem. Ciekawi mnie twoja ostatnia uwaga dotycząca: twojego namesrozwiązania. Zastanawiam się, czy istnieje jakikolwiek powód, aby podejrzewać, że organiczny, wbudowany w roztworze nadchodzi w niezbyt odległej przyszłości, czy powinniśmy po prostu przyjąć wbudowanej na rozwiązanie już przewidziane.
Dan
1
@ Dan Tak, jest. . To powiedziawszy, nie ma powodu, aby w międzyczasie nie przyjmować Nazw . Jest w pełni kompatybilny z konwencjami Emacsa, więc każdy pakiet używający Nazw może w dowolnym momencie przestać używać Nazw , a użytkownik nic nie wie.
Malabarba
Naprawdę powinieneś dodać namelessdo tej listy :) To świetny pomysł i bardzo starannie rozwiązuje problem.
Clément,
22

Ostatnim razem, gdy omawiano to na emacs-devel, dyskusja zakończyła się, gdy ludzie tacy jak Lars zauważyli, że lubią być w stanie M-x grepcoś zrobić. Dodanie przestrzeni nazw do Elisp nie powinno być zbyt trudne, ale uzyskanie wszystkich znanych narzędzi do ich prawidłowego zarządzania to kolejny problem.

Stefan
źródło
Myślę, że można to łatwo „naprawić”, tworząc aliasy dla najczęściej używanych wspólnych funkcji (lub wszystkich, być może)
Jesse
1
Konieczność „grep” pojawia się zwykle podczas opracowywania pakietu, ponieważ musisz wiedzieć, gdzie zmienna / funkcja może być używana w innych pakietach, więc może ona dotyczyć dowolnej dowolnej zmiennej / funkcji, a nie tylko określonych ważnych. Z tego powodu dodanie kilku aliasów nie będzie miało znaczenia. Innym powodem, dla którego mit nie pomoże, jest to, że dodanie aliasu nie pomoże ci znaleźć zastosowań, które nie używają tego aliasu.
Stefan,