Wersja 1.8 języka programowania Julia

Dostępna jest wersja języka programowania Julia 1.8, łącząca w sobie takie cechy, jak wysoka wydajność, obsługa dynamicznego pisania i wbudowane narzędzia do programowania równoległego. Składnia Julii jest zbliżona do MATLAB-a, zapożyczając niektóre elementy z Ruby i Lisp. Metoda manipulacji ciągami przypomina Perla. Kod projektu jest rozpowszechniany na licencji MIT.

Kluczowe cechy języka:

  • Wysoka wydajność: jednym z kluczowych celów projektu jest osiągnięcie wydajności zbliżonej do programów C. Kompilator Julia bazuje na pracach projektu LLVM i generuje wydajny natywny kod maszynowy dla wielu platform docelowych;
  • Obsługuje różne paradygmaty programowania, w tym elementy programowania obiektowego i funkcjonalnego. Biblioteka standardowa zapewnia między innymi funkcje asynchronicznego wejścia/wyjścia, kontroli procesów, rejestrowania, profilowania i zarządzania pakietami;
  • Typowanie dynamiczne: język nie wymaga jawnej definicji typów zmiennych, podobnie jak w przypadku skryptowych języków programowania. Obsługiwany tryb interaktywny;
  • Opcjonalna możliwość jawnego określenia typów;
  • Składnia idealna do obliczeń numerycznych, obliczeń naukowych, uczenia maszynowego i wizualizacji danych. Obsługa wielu numerycznych typów danych i narzędzi do zrównoleglenia obliczeń.
  • Możliwość bezpośredniego wywoływania funkcji z bibliotek C bez dodatkowych warstw.

Główne zmiany w Julii 1.8:

  • Nowe funkcje językowe
    • Pola modyfikowalnej struktury można teraz opisywać jako stałe, aby zapobiec ich zmianie i umożliwić optymalizację.
    • Adnotacje typów można dodawać do zmiennych globalnych.
    • Puste tablice n-wymiarowe można utworzyć, używając wielu średników w nawiasach kwadratowych, na przykład „[;;;]” tworzy tablicę 0x0x0.
    • Bloki Try mogą teraz opcjonalnie zawierać blok else, który jest wykonywany natychmiast po części głównej, jeśli nie zostały zgłoszone żadne błędy.
    • @inline i @noinline można umieścić wewnątrz treści funkcji, co pozwala na dodanie adnotacji do anonimowej funkcji.
    • @inline i @noinline można teraz zastosować do funkcji w witrynie lub bloku wywołań, aby wymusić uwzględnienie (lub nieuwzględnienie) odpowiednich wywołań funkcji.
    • ∀, ∃ i ∄ są dozwolone jako znaki identyfikacyjne.
    • Dodano obsługę specyfikacji Unicode 14.0.0.
    • Za pomocą metody Module(:name, false, false) można utworzyć moduł, który nie zawiera nazw, nie importuje bazy ani rdzenia ani nie zawiera odniesienia do samego siebie.
  • Zmiany w języku
    • Nowo utworzone obiekty Task (@spawn, @async itp.) mają teraz world_age dla metod z nadrzędnego zadania po utworzeniu, co pozwala na zoptymalizowane wykonanie. Poprzednia opcja aktywacji dostępna jest przy wykorzystaniu metody Base.invokelatest.
    • Dyrektywy niezrównoważonego dwukierunkowego formatowania Unicode są teraz zabronione w ciągach znaków i komentarzach, aby uniknąć wstrzyknięć.
    • Base.ifelse jest teraz zdefiniowany jako funkcja ogólna, a nie funkcja wbudowana, dzięki czemu pakiety mogą rozszerzać swoją definicję.
    • Każde przypisanie do zmiennej globalnej przechodzi teraz najpierw przez wywołanie funkcji konwersji(Any, x) lub konwersji(T, x), jeśli zmienna globalna została zadeklarowana jako typu T. Przed użyciem zmiennych globalnych upewnij się, że niezmienna konwersja(Any , x) === x jest zawsze prawdziwe, w przeciwnym razie może to prowadzić do nieoczekiwanego zachowania.
    • Funkcje wbudowane są teraz podobne do funkcji ogólnych i można je programowo wyliczyć przy użyciu metod.
  • Ulepszenia kompilatora/środowiska wykonawczego
    • Czas uruchamiania skrócony o około 25%.
    • Kompilator oparty na LLVM został oddzielony od biblioteki wykonawczej i utworzył nową bibliotekę libjulia-codegen. Jest ładowany domyślnie, więc podczas normalnego użytkowania nie powinno być żadnych zmian. We wdrożeniach, które nie wymagają kompilatora (na przykład obrazy systemu, w których cały niezbędny kod jest prekompilowany), tę bibliotekę (i jej zależność od LLVM) można po prostu pominąć.
    • Wnioskowanie o typie warunkowym jest teraz możliwe poprzez przekazanie argumentu do metody. Na przykład dla Base.ifelse(isa(x, Int), x, 0) zwraca ::Int, nawet jeśli typ x jest nieznany.
    • Ulepszono SROA (Scalar Measurement of Aggregates): eliminuje wywołania getfield z trwałymi polami globalnymi, eliminuje zmienne struktury z niezainicjowanymi polami, poprawia wydajność i obsługę zagnieżdżonych wywołań getfield.
    • Wnioskowanie o typach śledzi różne efekty — skutki uboczne i brak porzucania. Uwzględniana jest stała propagacja, co znacznie poprawia wydajność w czasie kompilacji. Na przykład w niektórych przypadkach wywołania funkcji, których nie można wstawić, ale które nie mają wpływu na wynik, zostaną odrzucone w czasie wykonywania. Reguły dotyczące efektów można nadpisać ręcznie za pomocą makra Base.@assume_effects.
    • Prekompilacja (z jawnymi dyrektywami prekompilacji lub określonymi obciążeniami) pozwala teraz zaoszczędzić więcej kodu zdefiniowanego pod względem typu, co skutkuje szybszym wykonaniem za pierwszym razem. Wszelkie nowe kombinacje metod/typów wymagane przez Twój pakiet, niezależnie od tego, gdzie te metody zostały zdefiniowane, mogą teraz być buforowane w pliku prekompilacji, jeśli są wywoływane przez metodę należącą do Twojego pakietu.
  • Zmiany w opcjach wiersza poleceń
    • Domyślnym zachowaniem monitorowania deklaracji @inbounds jest teraz opcja auto w „--check-bounds=yes|no|auto”.
    • Nowa opcja „--strip-metadata” umożliwiająca usuwanie dokumentów, informacji o lokalizacji źródłowej i nazw zmiennych lokalnych podczas tworzenia obrazu systemu.
    • Nowa opcja „--strip-ir” umożliwiająca kompilatorowi usunięcie pośredniej reprezentacji kodu źródłowego podczas budowania obrazu systemu. Wynikowy obraz będzie działał tylko wtedy, gdy zostanie użyte „--compile=all” lub jeśli cały wymagany kod zostanie wstępnie skompilowany.
    • Jeśli zamiast nazwy pliku zostanie podany znak „-”, wówczas kod wykonywalny zostanie odczytany ze standardowego strumienia wejściowego.
  • Zmiany w obsłudze wielowątkowości
    • Threads.@threads domyślnie używa nowej opcji planowania :dynamic, która różni się od poprzedniego trybu tym, że iteracje będą planowane dynamicznie dla dostępnych wątków roboczych, a nie przypisywane do każdego wątku. Ten tryb pozwala na lepszą dystrybucję zagnieżdżonych pętli za pomocą @spawn i @threads.
  • Nowe funkcje biblioteczne
    • eachsplit(str) aby wykonać split(str) wiele razy.
    • allequal(itr), aby sprawdzić, czy wszystkie elementy w iteratorze są równe.
    • hardlink(src, dst) może służyć do tworzenia twardych linków.
    • setcpuaffinity(cmd, cpus) aby ustawić powinowactwo rdzenia procesora do uruchomionych procesów.
    • discstat(path=pwd()), aby uzyskać statystyki dysku.
    • Nowe makro @showtime wyświetlające zarówno ocenianą linię, jak i raport @time.
    • Dodano makro LazyString i leniwe"str" ​​w celu obsługi leniwego konstruowania komunikatów o błędach w ścieżkach błędów.
    • Naprawiono problem współbieżności w Dict i innych obiektach pochodnych, takich jak klucze (::Dict), wartości (::Dict) i Set. Metody iteracyjne można teraz wywoływać na słowniku lub zestawie, o ile nie ma żadnych wywołań modyfikujących słownik lub zestaw.
    • @time i @timev mają teraz opcjonalny opis, pozwalający na przykład na adnotację o źródle raportów czasowych. @time „Ocenianie foo” foo().
    • range przyjmuje stop lub długość jako jedyny argument słowa kluczowego.
    • precyzja i setprecision akceptują teraz base jako słowo kluczowe
    • Obiekty gniazd TCP udostępniają teraz metodę Closewrite i obsługują tryb półotwarty.
    • ekstrema akceptuje teraz argument init.
    • Iterators.countfrom akceptuje teraz dowolny typ, który definiuje metodę +.
    • @time przydziela teraz % czasu spędzonego na ponownej kompilacji metod ze zmienionymi typami.
  • Zmiany w bibliotece standardowej
    • Klucze z wartością Nic nie jest teraz usuwane ze środowiska w dodatku.
    • Iterators.reverse (a zatem last) obsługuje każdą linię.
    • Funkcja długości dla zakresów niektórych typów nie sprawdza już przepełnienia liczb całkowitych. Dostępna jest nowa funkcja CHECK_length, która zawiera logikę kontroli transferu bitów. Jeśli to konieczne, użyj pliku SaferIntegers.jl, aby skonstruować typ zakresu.
    • Iterator Iterators.Reverse implementuje odwrócenie każdego indeksu, jeśli to możliwe.
  • Menedżer pakietów
    • Nowe wskaźniki ⌃ i ⌅ przy pakietach w statusie „pkg>”, dla których dostępne są nowe wersje. ⌅ wskazuje, że nie można zainstalować nowych wersji.
    • Nowy nieaktualny argument::Bool do Pkg.status (--outdated lub -o w trybie REPL), aby pokazać informacje o pakietach z poprzednich wersji.
    • Nowy argument compat::Bool do Pkg.status (--compat lub -c w trybie REPL), aby pokazać dowolne wpisy [compat] w Project.toml.
    • Nowy tryb „pkg>compat” (i Pkg.compat) do ustawiania wpisów zgodności projektu. Udostępnia interaktywny edytor poprzez „pkg>compat” lub bezpośrednią kontrolę rekordów poprzez „pkg>Foo 0.4,0.5”, który może ładować bieżące rekordy poprzez uzupełnianie zakładek. Oznacza to, że „pkg> compat Fo” jest automatycznie aktualizowane do „pkg> Foo 0.4,0.5”, dzięki czemu można edytować istniejący wpis.
    • Pkg próbuje teraz pobrać pakiety z serwera pakietów tylko wtedy, gdy serwer monitoruje rejestr zawierający pakiet.
    • Pkg.instantiate będzie teraz wyświetlać ostrzeżenie, gdy Project.toml nie będzie zsynchronizowany z Manifest.toml. Robi to w oparciu o skrót rekordów deps i compat projektu (inne pola są ignorowane) w manifeście podczas jego rozwiązywania, dzięki czemu wszelkie zmiany w rekordach deps lub compat Project.toml mogą zostać wykryte bez ponownego rozpoznawania.
    • Jeśli polecenie „pkg>add” nie może znaleźć pakietu o podanej nazwie, zasugeruje teraz pakiety o podobnych nazwach, które można dodać.
    • Wersja Julii przechowywana w manifeście nie zawiera już numeru kompilacji, co oznacza, że ​​master będzie teraz zapisywany jako 1.9.0-DEV.
    • Przerwanie testu „pkg>” będzie teraz wykrywane bardziej konsekwentnie i zostanie poprawnie zwrócone do REPL.
  • Narzędzia interaktywne
    • Nowe makro @time_imports do raportowania czasu spędzonego na importowaniu pakietów i ich zależności, podkreślając czas kompilacji i rekompilacji jako procent importu.
  • Algebra liniowa
    • Podmoduł BLAS obsługuje teraz funkcje BLAS spr! poziomu 2.
    • Biblioteka standardowa LinearAlgebra.jl jest teraz całkowicie niezależna od SparseArrays.jl, zarówno z punktu widzenia kodu źródłowego, jak i testów jednostkowych. W rezultacie rzadkie tablice nie są już zwracane (domyślnie) przez metody z LinearAlgebra zastosowane do obiektów Base lub LinearAlgebra. W szczególności prowadzi to do następujących istotnych zmian:
      • Konkatenacje wykorzystujące specjalne „rzadkie” macierze (np. diagonalne) zwracają teraz gęste macierze; W rezultacie pola D1 i D2 obiektów SVD utworzone przez wywołania getproperty są teraz gęstymi macierzami.
      • Metoda podobna(::SpecialSparseMatrix, ::Type, ::Dims) zwraca gęstą macierz zerową. W konsekwencji produkty dwu-, trzy- i symetrycznych macierzy trójdiagonalnych między sobą prowadzą do powstania gęstej macierzy. Ponadto konstruowanie podobnych macierzy z trzema argumentami ze specjalnych „rzadkich” macierzy z (niestatycznych) macierzy kończy się teraz niepowodzeniem z powodu „zero(::Type{Matrix{T}})”.
  • Drukuj
    • %s i %c używają teraz argumentu szerokości tekstu do formatowania szerokości.
  • Profil
    • Profilowanie obciążenia procesora rejestruje teraz metadane, w tym wątki i zadania. Funkcja Profile.print() ma nowy argument groupby, który umożliwia grupowanie wątków, zadań lub podwątków/zadań, zadań/wątków oraz wątków i argumentów zadań w celu zapewnienia filtrowania. Ponadto procent wykorzystania jest teraz raportowany ogółem lub według wątku, w zależności od tego, czy wątek jest bezczynny, czy nie w każdej próbce. Funkcja Profile.fetch() domyślnie zawiera nowe metadane. Aby zapewnić kompatybilność wsteczną z zewnętrznymi odbiorcami danych profilowania, można to wykluczyć, przekazując include_meta=false.
    • Nowy moduł Profile.Allocs umożliwia profilowanie alokacji pamięci. Rejestrowany jest ślad stosu dotyczący typu i rozmiaru każdej alokacji pamięci, a argument sample_rate umożliwia pominięcie konfigurowalnej liczby alokacji, co zmniejsza obciążenie wydajności.
    • Użytkownik może teraz uruchamiać profilowanie procesora o stałym czasie trwania podczas wykonywania zadań bez uprzedniego ładowania profilu, a raport będzie wyświetlany podczas działania. W systemie MacOS i FreeBSD naciśnij ctrl-t lub wywołaj SIGINFO. W przypadku innych platform aktywuj SIGUSR1, tj. % zabicia -USR1 $julia_pid. Ta funkcja nie jest dostępna w systemie Windows.
  • ODPOWIEDŹ
    • RadioMenu obsługuje teraz dodatkowe skróty klawiaturowe umożliwiające bezpośredni wybór opcji.
    • Sekwencja „?(x, y”, po której następuje naciśnięcie klawisza TAB, wyświetla wszystkie metody, które można wywołać z argumentami x, y, .... (Początkowa spacja uniemożliwia przejście do trybu pomocy.) „MójModuł.?(x, y " ogranicza wyszukiwanie do "MójModuł". Naciśnięcie TAB wymaga, aby co najmniej jeden argument był typu bardziej szczegółowego niż Any. Lub użyj SHIFT-TAB zamiast TAB, aby zezwolić na dowolne kompatybilne metody.
    • Nowa zmienna globalna err pozwala uzyskać najnowszy wyjątek, podobnie jak zachowanie ans z ostatnią odpowiedzią. Wprowadzenie błędu powoduje ponowne wydrukowanie informacji o wyjątku.
  • Rzadkie tablice
    • Przeniesiono kod SparseArrays z repozytorium Julia do zewnętrznego repozytorium SparseArrays.jl.
    • Nowe funkcje łączenia sparse_hcat, sparse_vcat i sparse_hvcat zwracają typ SparseMatrixCSC niezależnie od typów argumentów wejściowych. Stało się to konieczne, aby ujednolicić mechanizm sklejania macierzy po oddzieleniu kodu LinearAlgebra.jl i SparseArrays.jl.
  • Logowanie
    • Standardowe poziomy rejestrowania BelowMinLevel, Debug, Info, Warn, Error i AboveMaxLevel są teraz eksportowane ze standardowej biblioteki Logging.
  • Unicode
    • Dodano funkcję isequal_normalized do sprawdzania równoważności Unicode bez jawnego konstruowania znormalizowanych ciągów znaków.
    • Funkcja Unicode.normalize akceptuje teraz słowo kluczowe charttransform, którego można użyć do zapewnienia niestandardowych mapowań znaków, a funkcja Unicode.julia_chartransform umożliwia także odtworzenie mapowania używanego, gdy parser Julii normalizuje identyfikatory.
  • Testowanie
    • „@test_throws „jakaś wiadomość” wyzwalacza_error()” może być teraz użyta do sprawdzenia, czy wyświetlany tekst błędu zawiera błąd „jakaś wiadomość”, niezależnie od konkretnego typu wyjątku. Obsługiwane są także wyrażenia regularne, listy ciągów i funkcje dopasowujące.
    • Można teraz użyć @testset foo() do utworzenia zestawu testowego na podstawie danej funkcji. Nazwa przypadku testowego to nazwa wywoływanej funkcji. Wywoływana funkcja może zawierać definicje @test i inne definicje @testset, w tym na potrzeby wywołań innych funkcji, przy jednoczesnym rejestrowaniu wszystkich pośrednich wyników testów.
    • TestLogger i LogRecord są teraz eksportowane ze standardowej biblioteki testowej.
  • Rozproszone
    • SSHManager obsługuje teraz wątki robocze z opakowaniem csh/tcsh za pomocą metody addprocs() i parametru powłoki=:csh.
  • Inne zmiany
    • GC.enable_logging(true) może służyć do rejestrowania każdej operacji usuwania elementów bezużytecznych wraz z czasem i ilością zebranej pamięci.

Źródło: opennet.ru

Dodaj komentarz