W matematyce mnożenie macierzy lub iloczyn macierzy jest operacją binarną, która wytwarza macierz z dwóch macierzy. Definicja jest motywowana równaniami liniowymi i transformacjami liniowymi wektorów, które mają wiele zastosowań w matematyce, fizyce i inżynierii. Bardziej szczegółowo, jeśli A jest macierzą n × m, a B jest macierzą m × p, to ich iloczyn macierzy AB jest macierzą n × p, w której m wpisów w rzędzie A jest pomnożonych przez m wpisów w dół a kolumny B i zsumowane, aby uzyskać wpis AB. Gdy dwie transformacje liniowe są reprezentowane przez macierze, to iloczyn macierzy reprezentuje skład tych dwóch transformacji.
Źródło: Wikipedia
Innymi słowy, aby pomnożyć dwie macierze, na przykład:
1 2 3 1 4
2 3 4 × 3 1 =
3 4 5 4 6
Najpierw weź wiersz 1 w pierwszej macierzy, kolumnę numer 1 w drugiej macierzy i pomnóż 1
przez 1
, 2
przez 3
i 3
przez 4
.
1 × 1 = 1
2 × 3 = 6
3 × 4 = 12
Teraz dodaj je razem, aby otrzymać swój pierwszy przedmiot:
1 2 3 1 4 19
2 3 4 × 3 1 =
3 4 5 4 6
W przypadku drugiej liczby w pierwszej kolumnie wyniku musisz wziąć wiersz 2 zamiast wiersza 1 i zrobić to samo.
1 × 2 = 2
3 × 3 = 9
4 × 4 = 16
= 27
Po wykonaniu całej pierwszej kolumny wynik wygląda następująco:
1 2 3 1 4 19
2 3 4 × 3 1 = 27
3 4 5 4 6 35
Teraz zrób dokładnie to samo, ale weź drugą kolumnę zamiast pierwszej kolumny, co spowoduje:
1 2 3 1 4 19 24
2 3 4 × 3 1 = 27 35
3 4 5 4 6 35 46
Twoje zadanie
Biorąc pod uwagę dwie macierze (maksymalne wymiary 200 x 200), zawierające liczby z zakresu od -10000 do 10000, gdzie liczba kolumn na pierwszej równa się liczbie wierszy na drugiej, pomnóż pierwszą przez drugą. (Mnożenie macierzy jest nieprzemienne.)
Możesz pobierać dane wejściowe i podawać dane wyjściowe jako tablicę tablic (lub odpowiednik), macierz (jeśli twój język ma ten format) lub łańcuch wielowierszowy.
Nie można używać żadnych wbudowanych funkcji do mnożenia macierzy.
Przypadki testowe
1 2 1 2 3 4 5 13 16 19 22 25
3 4 × 6 7 8 9 10 = 27 34 41 48 55
5 6 41 52 63 74 85
2 3 3 5 15 13
3 4 × 3 1 = 21 19
5 3 11 27
1 3 1 3 7 15
9 3 × 2 4 = 15 39
1 -1000 -1999 -3997
Pamiętaj, to jest kodowanie w golfa , więc wygrywa kod z najmniejszą liczbą bajtów.
Odpowiedzi:
Galaretka ,
75 bajtówStaje B i A jako argumenty i zwraca A × B .
Wypróbuj online!
Jak to działa
źródło
æ×
, który ma 2 bajty.æ.
atomu.05AB1E , 13 bajtów
Wypróbuj online!
Wyjaśnienie
źródło
εUøεX*O
Python 2,
6966 bajtówJest to zgodne ze standardową formułą, ale dla zwięzłości lambda-d :) Kod bez golfa jest bardzo prosty!
Dzięki Alexi Torhamo za uratowanie 3 bajtów! :)
Nieskluczony kod:
źródło
sum(map(int.__mul__,r,c))
aby zapisać 3 bajty. (Nie będzie działać z zmiennoprzecinkowym, ale to też nie było wymagane)J,
139 bajtówZaoszczędzone 4 bajty dzięki kilometrom!
To jest widelec z czapką:
Co odpowiada:
Który wykonuje pożądane mnożenie; są one następnie sumowane.
Z wbudowanym produktem kropkowym, 5 bajtów:
+/ .*
Przypadki testowe
źródło
[:+/*"#:~
na 9 bajtówHaskell ,
57 5654 bajtówWypróbuj online!
Stosowanie:
foldr(zipWith(:))e
ze=[]:e
jest krótszą formątranspose
.źródło
Haskell , 45 bajtów
Wypróbuj online!
Przyjmuje argumenty w odwrotnej kolejności.
źródło
R, 66 bajtów
Nienazwana funkcja przyjmuje dwie macierze R jako dane wejściowe i zwraca produkt. Wykorzystuje,
apply
który służy do stosowania funkcji na marginesach tablic. Wfor
tym przypadku działa tylko jako podwójna pętla: dla każdej kolumnyB
i dla każdego wierszaA
zwraca sumę (wektoryzowanych) produktów.Porównaj z podejściem czystym dla pętli (
101
bajty):źródło
outer(A,B,`*`)
niż wbudowaneapply
połączenia?Mathematica, 20 bajtów
Funkcja anonimowa. Pobiera na wejściu dwie listy liczb rangi 2 i zwraca dane liczbowe rangi 2 jako dane wyjściowe. Dla tych, którzy są ciekawi,
Inner
jest funkcją, która wykonuje podobne do mnożenia macierzy zastosowanie dwóch funkcji do dwóch tensorów.źródło
Inner[1##&,##]&
jest równoważne zInner[1##&,##,Plus]&
... I tak1##&~Inner~##&
byłoby jeszcze lepiej.C #,
168167 bajtówDziękuję @Mukul Kumar za zapisanie 1 bajtu, tym razem pętla while była krótsza: P
Pełny program z przypadkami testowymi:
źródło
for(;i<n;)
->while(i<n)
mają po 10 bajtów.for (;i <n;i++)
->while (i++<n)
zapisuje 1 bajtMATL ,
1211 bajtówMacierze są wprowadzane przy użyciu
;
jako separatora wierszy.Wypróbuj online!
Mnożenie macierzy bez wbudowanego było częścią mojej odpowiedzi na Showcase of languages . Jednak, gdy próbowałem ponownie użyć oryginalnego kodu dla tej odpowiedzi, zdałem sobie sprawę, że wystąpił błąd (wyjście wektora wiersza zostało niepoprawnie przekonwertowane na wektor kolumny). To jest teraz poprawione, zarówno tu i tam. Aby dowiedzieć się, jak działa kod, zobacz polecony post (fragment o długości 11).
źródło
C ++ 14,
173168156146 bajtówC.back()
zamiast tego liczenia nai
C.clear()
i wymaganieC
pustego na początkuJako nienazwana lambda:
Wymaga wejścia i wyjścia, ponieważ
vector<vector<int>>
dane wyjściowe muszą być wcześniej puste.Nie golfowany:
Próba:
źródło
push_back()
zamiastemplace_back()
?Łuska ,
76 bajtówZwróć uwagę na kolejność argumentów, spróbuj online!
-1 bajt dzięki @Zgarb!
Wyjaśnienie
Zasadniczo po prostu robiąc to, co definiuje mnożenie macierzy:
źródło
oΣz
może byćδṁ
JavaScript (ES6), 66 bajtów
źródło
C #, 131 bajtów
Ukradłem rozwiązanie Yodle przy założeniu, że mogę napisać to bardziej efektywnie przy użyciu LINQ (w przeciwieństwie do pętli). Podjąłem kilka prób, ale trochę to zmiażdżyłem.
Tutaj jest to trochę podzielone:
Jedynym prawdziwym „trik” tutaj jest transpozycją macierzy
B.First().Select((f, i) => B.Select(r => r.ElementAt(i)))
. Po transponowaniu drugiej macierzy mamy dwie tabliceA[i,x]
iB[j,x]
. Weź iloczyn kartezjański (i*j
) i spakuj razem każdą z tychx
tablic długości.Kod testowy:
źródło
using System.Linq
; Nie jestem pewien, czy rozwiązania tutaj muszą obejmować płytę kotłową jakusing System
istatic void Main()
Haskell , 49 bajtów
Wypróbuj online!
Dane wejściowe i wyjściowe są listami kolumn. Odwzorowuje każdą kolumnę drugiej macierzy na ten wiersz, spakowany z kolumnami pierwszej macierzy i skalując każdą, zsumowaną jako wektor.
Wydaje mi się, że musi istnieć dobry sposób, aby uczynić to bezcelowym i zaoszczędzić garść bajtów, ale jeszcze go nie widzę.
źródło
JavaScript, 128 bajtów
Otrzymujesz wynik, po prostu sprawdzając $ - to trochę oszustwo, ale hej, zaoszczędziłem kilka bajtów.
źródło
PHP, 110 bajtów
Trzy pętle dla elfich tablic. To takie proste ... ale golf nie ma wiele do zaoferowania.
źródło
Tak właściwie 14 bajtów
Zapraszamy do gry w golfa! Wypróbuj online!
Ungolfing
źródło
C, 618 bajtów
Nazwana funkcja i autor: zdecydowanie najdłuższe przesyłanie tutaj, częściowo ze względu na fakt, że przekształcanie danych wejściowych tablicy znaków na dwuwymiarowe tablice liczb całkowitych C zajmuje najwięcej bajtów, a także dlatego, że nie grałem w golfa w C przez najdłuższy czas. Nadal pracuję nad tym, aby skrócić to tak bardzo, jak potrafię, a wszelkie wskazówki w tym zakresie są bardzo mile widziane.
Teraz, nie wchodząc w to, pobiera dane wejściowe przez wiersz poleceń z dwiema macierzami reprezentowanymi przez dwa ciągi znaków, z których każdy zawiera wiersze oddzielone przecinkami, a każdy wiersz reprezentuje liczby całkowite oddzielone spacjami. Na przykład macierze:
będzie wprowadzony jako:
./a.out "1 2 3,4 5 6,7 8 9" "44 52,67 -79,83 90"
Otrzymana macierz jest wyprowadzana do STDOUT jako ciąg wielowierszowy. Na przykład dane wyjściowe dla powyższego wejścia to:
źródło
Clojure, 60 bajtów
Wiele bajtów wydanych na transpozycję drugiego argumentu.
źródło
Ruby , 59 bajtów
Wypróbuj online!
źródło