Utwórz N-wymiarowy simpleks (czworościan)

12

Najprostszym N-wymiarowym kształtem, jaki można stworzyć dla dowolnego wymiaru, jest Simplex i jest to zestaw punktów N + 1, które są w równej odległości od siebie.

Dla 2 wymiarów jest to trójkąt równoboczny, dla 3 wymiarów jest to zwykły czworościan, przy 4 wymiarach jest to 5 komórek i tak dalej.

Wyzwanie

Biorąc pod uwagę wymiar całkowity N jako dane wejściowe, wyślij tablicę / listę / stos / cokolwiek z N punktów wymiarowych, które reprezentują simpleks tego wymiaru. Oznacza to, że N + 1 wierzchołki są równe i niezerowa odległość od siebie.

Referencyjne wdrożenie w Lua

Przykłady

1 -> [[0], [1]]
2 -> [[0, 0], [1, 0], [0.5, 0.866...]]
4 -> [[0, 0, 0, 0], [1, 0, 0, 0], [0.5, 0.866..., 0, 0], [0.5, 0.288..., 0.816..., 0], [0.5, 0.288..., 0.204..., 0.790...]]

Notatki

  • Dane wejściowe są liczbą w dowolnym standardowym formacie i zawsze będą liczbami całkowitymi większymi niż 1 i mniejszymi niż 10
  • Kodowanie jest dozwolone dla wejścia 1, ale nic wyższego.
  • Rozsądny błąd jest dozwolony w danych wyjściowych. Problemy z arytmetyką zmiennoprzecinkową lub wyzwalaczem można zignorować.
  • Dozwolona jest dowolna transformacja simpleksowego wymiaru N, pod warunkiem, że pozostaje ona regularna i niezerowa.
  • Standardowe luki są zabronione.
  • To jest , więc wygrywa najmniej bajtów.
ATaco
źródło
1
Zdajesz sobie sprawę, że nie możesz wymusić odpowiedzi na kod nie na stałe? Najprostszym sposobem uniknięcia tego jest zwiększenie zakresu danych wejściowych. Również „ważne kryteria muszą być obiektywne”, rozsądne nie jest obiektywne.
user202729
Wygląda na to, że można to rozwiązać, biorąc macierz tożsamości plus jeden dodatkowy wektor, którego wpisy są równe.
xnor
@xnor to zrobił;)
PattuX

Odpowiedzi:

4

Galaretka , 11 bajtów

‘½‘÷ẋW
=þ;Ç

Wypróbuj online!

Działa poprzez wygenerowanie macierzy tożsamości o rozmiarze N i powiązanie jej z listą wygenerowaną przez powtórzenie N razy singletonu √ (N + 1) + 1 , podzielone przez N .

‘½‘÷ẋW – Helper link (monadic). I'll call the argument N.

‘      – Increment N (N + 1).
 ½     – Square root.
  ‘    – Increment (√(N + 1) + 1).
   ÷   – Divide by N.
    ẋ  – Repeat this singleton list N times.
     W – And wrap that into another list.

––––––––––––––––––––––––––––––––––––––––––

=þ;Ç   – Main link.

=þ     – Outer product of equality.
  ;Ç   – Concatenate with the result given by the helper link applied to the input.
Pan Xcoder
źródło
5

Python 78 66 bajtów

lambda n:[i*[0]+[n]+(n+~i)*[0]for i in range(n)]+[n*[1+(n+1)**.5]]

Z pewnością można to poprawić, szczególnie przy obsłudze n = 1 ''. (Jak to jest nawet simplex?) Właśnie zdałem sobie sprawę, że to nie jest konieczne. Prawdopodobnie można go jeszcze poprawić ^^

Wypróbuj online!

[i*[0]+[1]+(n+~i)*[0]for i in range(n)]tworzy matrycę tożsamości. Wszystkie punkty mają odległość sqrt(2)od siebie. (dzięki Rod za ulepszenie)

Teraz potrzebujemy n+1-tego punktu o tej samej odległości od wszystkich innych punktów. Musimy wybrać (x, x, ... x).

Odległość od (1, 0, ... )do (x, x, ... x)jest sqrt((x-1)²+x²+...+x²). Jeśli chcemy się nwymiarową simplex to okazuje się sqrt((x-1)²+(n-1)x²), jak mamy jeden 1i n-1 0S w pierwszym punkcie. Uprość trochę:sqrt(x²-2x+1+(n-1)x²) = sqrt(nx²-2x+1)

Chcemy, aby ta odległość była sqrt(2).

sqrt(2) = sqrt(nx²-2x+1)
2 = nx²-2x+1
0 = nx²-2x-1
0 = x²-2/n*x+1/n

Rozwiązanie tego równania kwadratowego (jedno rozwiązanie, drugie też działa dobrze):

x = 1/n+sqrt(1/n²+1/n) = 1/n+sqrt((n+1)/n²) = 1/n+sqrt(n+1)/n = (1+sqrt(n+1))/n

Umieść to na liście n razy, umieść tę listę na liście i dołącz do macierzy tożsamości.


-4 Bajty dzięki Alexowi Vargie:

Pomnóż każdy wektor przez n. Zmienia to tworzenie macierzy tożsamości na lambda n:[i*[0]+[n]+(n+~i)*[0](tę samą długość) i pozbywa się podziału nw dodatkowym punkcie, więc staje się n*[1+(n+1)**.5], zapisując dwa nawiasy i /n.

PattuX
źródło
Chociaż nie są objęte zakresem tego wyzwania, prostokąty 0 wymiarowe są również rzeczą, choć może to zabrzmieć okropnie.
ATaco
Po przeczytaniu nieco więcej, czy każda para różnych liczb nie jest 1-simpleks?
PattuX
Tak, taka jest irytująca moc
simpleksów
1
Możesz zmienić sposób generowania macierzy tożsamości, aby zaoszczędzić 8 bajtów
Rod
1
66 bajtów łączących poprzednie komentarze
Alex Varga,
2

APL (Dyalog) , 20 18 bajtów

1 bajt dzięki @ngn

∘.=⍨∘⍳⍪1÷¯1+4○*∘.5

Wypróbuj online!

Uriel
źródło
(∘.=⍨⍳)->∘.=⍨∘⍳
ngn
@ngn Mam tego golfa w gotowości, czekałem, czy mogę zagrać w golfa jeszcze kilka bajtów, zanim włożyłem to, ponieważ edytowanie postów jest naprawdę bolesne przy użyciu telefonu komórkowego
Uriel
Pozwoliłem ci go edytować. Też podejrzewam, że może być lepsza odpowiedź - przypomina mi to, ale nie mogę do końca zrozumieć, jak to może działać ...
ngn
podział matrycy był bezowocny, ale znalazłem ciekawą funkcję kołową:{÷¯1+4○⍵*.5}⍪⍳∘.=⍳
ngn
@ngn dzięki. Użyłem milczącej wersji twojego rozwiązania dla tej samej liczby
Uriel
1

JavaScript (ES7), 70 bajtów

n=>[a=Array(n++).fill((1+n**.5)/--n),...a.map((_,i)=>a.map(_=>+!i--))]

Port odpowiedzi Python na @ PattuX.

Neil
źródło
1

Wolfram Language (Mathematica), 205 bajtów

f1 = Sqrt[# (# + 1)/2]/# /(# + 1) & ;
f2 = Sqrt[# (# + 1)/2]/# & ;
simplex[k_] := {ConstantArray[0, k]}~Join~Table[
   Table[f1[n], {n, 1, n - 1}]~Join~{f2[n]}~Join~
    ConstantArray[0, k - n],
   {n, k}]

Funkcja Simplex w Mathematica Począwszy od {0,0,...]},{1,0,0,...]}, Umieszczenie pierwszego punktu na początku, Drugi punkt na xosi Trzeci punkt na x,ypłaszczyźnie, Czwarty punkt w x,y,zprzestrzeni itp. Postęp ten powoduje ponowne wykorzystanie wszystkich poprzednich punktów, dodając jeden nowy punkt na raz w nowym wymiarze

simplex[6]={{0, 0, 0, 0, 0, 0}, {1, 0, 0, 0, 0, 0}, {1/2, Sqrt[3]/2, 0, 0, 0, 
  0}, {1/2, 1/(2 Sqrt[3]), Sqrt[2/3], 0, 0, 0}, {1/2, 1/(2 Sqrt[3]), 
  1/(2 Sqrt[6]), Sqrt[5/2]/2, 0, 0}, {1/2, 1/(2 Sqrt[3]), 1/(
  2 Sqrt[6]), 1/(2 Sqrt[10]), Sqrt[3/5], 0}, {1/2, 1/(2 Sqrt[3]), 1/(
  2 Sqrt[6]), 1/(2 Sqrt[10]), 1/(2 Sqrt[15]), Sqrt[7/3]/2}}

Weryfikacja

In[64]:= EuclideanDistance[simplex[10][[#[[1]]]],simplex[10][[#[[2]]]]] & /@ Permutations[Range[10],{2}]//Simplify
Out[64]= {1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}
Russell Chipman
źródło
1
Witamy na stronie! 1) To jest golfowy kod, powinieneś dążyć do tego, aby Twój kod był jak najkrótszy. 2) Użyj Markdown, aby twój post był jak najbardziej czytelny.
caird coinheringaahing
0

Rubinowy , 55 bajtów

zamiast zwracać podobne wielkości dla wszystkich wymiarów i używając wzoru (1+(n+1)**0.5)/nI skaluję w górę o współczynnik, naby uprościć wzór(1+(n+1)**0.5)

->n{(a=[n]+[0]*~-n).map{a=a.rotate}+[[1+(n+1)**0.5]*n]}

Wypróbuj online!

nie wziął udziału w programie testowym

Funkcja lambda przyjmuje njako argument i zwraca tablicę tablic.

f=->n{
  (a=[n]+[0]*~-n).map{        #setup an array `a` containing `n` and `n-1` zeros. perform `n` iterations (which happens to be the the size of the array.)
  a=a.rotate}+                #in each iteration rotate `a` and return an array of all possible rotations of array `a`     
  [[1+(n+1)**0.5]*n]          #concatenate an array of n copies of 1+(n+1)**0.5
}

p f[3]                        # call for n=3 and print output

wynik

[[0, 0, 3], [0, 3, 0], [3, 0, 0], [3.0, 3.0, 3.0]]
Level River St
źródło
0

R , 38 bajtów

function(n)rbind(diag(n,n),1+(n+1)^.5)

Wypróbuj online!

Giuseppe
źródło