2B Matris Döndürme


30

Diyelim ki aşağıdaki (2B) matrisim var:

[[1,  2,  3,  4 ],
 [5,  6,  7,  8 ],
 [9,  10, 11, 12],
 [13, 14, 15, 16]]

Matrisi saatin tersi yönünde döndürün R(90 derecelik artışlarla değil, her seferinde yalnızca 1 sayı),

1  2  3  4             2 3   4  8         3   4   8  12
5  6  7  8    -->      1 7  11 12   -->   2  11  10  16 
9  10 11 12            5 6  10 16         1   7   6  15 
13 14 15 16            9 13 14 15         5   9  13  14

Tamamlanan örnek:

Giriş:

2
[[1,  2,  3,  4 ],
 [5,  6,  7,  8 ],
 [9,  10, 11, 12],
 [13, 14, 15, 16]]

Çıktı:

[[3,  4,  8, 12],
 [2, 11, 10, 16],
 [1,  7,  6, 15],
 [5,  9, 13, 14]]

(garip boşluklar sayıları güzel sütunlarda hizalamak içindir)

Matrisin dış "halkası" saat yönünün tersine 2 döndürür ve iç sağ da 2 döndürür. Bu matriste sadece iki halka var.

1 "ring" içeren bir örnek:

2
[[1, 2],
 [3, 4],
 [5, 6]]

Çıkması gerekir:

[[4, 6],
 [2, 5],
 [1, 3]]

Buradaki zorluk, bir matris ve bir tamsayı almak Rve çevrildikten sonra çevrilmiş halini almak R.

4x5'lik bir matrisin dönmesi aşağıdaki şekilde gösterilir: görüntü tanımını buraya girin

Kısıtlamalar:

  • 2 ≤ M, N ≤ 100M ve N, matrisin boyutlarıdır. Minimum M ve N'nin bile olacağı garantilidir.
  • 1 ≤ R ≤ 80, burada r, dönüşlerin sayısıdır.
  • Matris sadece pozitif tamsayılar içerecektir.
  • Değerler her zaman belirgin değildir.
  • Girdi her zaman 2B dizisi olmalıdır (2B dizisi olarak çalışma zamanı girdisini alamıyorsanız, giriş almak için başka bir yol bulmanız gerekir).

Belirsiz değerleri olan başka bir test durumu:

1
[[1, 1],
 [2, 2],
 [3, 3]]

Çıktılar:

[[1, 2],
 [1, 3],
 [2, 3]]

Bu , bu yüzden en kısa cevap kazanır!





4
@ceasedtoturncounterclockwis İsminiz bu zorluk için çok ironik ...
HyperNeutrino

1
[[3, 4, 8, 12], [2, 11, 10, 16], [1, 7, 6, 16], [5, 9, 13, 14]]16 birdenbire olması gerektiği tahmin yineleniyor: [[3, 4, 8, 12], [2, 11, 10, 16], [1, 7, 6, 15], [5, 9, 13, 14]]?
Christoph

Yanıtlar:



5

Octave, 210 bayt

function M=F(M,R);f=@(z)[-z/2:-1 !eye(!!mod(z,2)) 1:z/2];t=angle(f([x y]=size(M))'+f(y)*i);B=!!M;B(2:x-1,2:y-1)=0;d=bwdist(B,'ch');[~,I]=sortrows([d(:) t(:)]);for k=0:max(d(:));M(h)=shift(M(h=I(d(I)==k)),R);end

Octave Online'da deneyin!

Ungolfed versiyonu:

function M=F(M,R)
    [x y]=size(M);
    f=@(z)[-z/2:-1 !eye(!!mod(z,2)) 1:z/2];
    t=angle(f(x)'+f(y)*i);
    B=!!M;
    B(2:x-1,2:y-1)=0;
    d=bwdist(B,'chessboard');
    [~,I]=sortrows([d(:) t(:)]);
    for k=0:max(d(:))
        M(h)=shift(M(h=I(d(I)==k)),R);
    end
end
R=2;
M=randi(10,4,7)
F(M,R)

Açıklama:

f=@(z)[-z/2:-1 !eye(!!mod(z,2)) 1:z/2]; 

Sayı alan ve girdi 4 (çift) için sıralı ve ortalanmış bir aralık üreten bir işlev -2 -1 1 2
girdi 5 (tek) için üretir, -2.5 -1.5 0 1 2
sadece sıralanmalı ve merkezlenmelidir

f(x)'+f(y)*i    

aralıklardan üretilen karmaşık bir matris

(-2,-2.5) (-2,-1.5) (-2,0) (-2,1) (-2,2)
(-1,-2.5) (-1,-1.5) (-1,0) (-1,1) (-1,2)
(1,-2.5)  (1,-1.5)  (1,0)  (1,1)  (1,2)
(2,-2.5)  (2,-1.5)  (2,0)  (2,1)  (2,2)

t=angle(f(x)'+f(y)*i);                    

Dikdörtgeni kutupsal koordinatlara ve dönüş açılarını dönüştürün, böylece her halka açısı için saat yönünün tersine sıralanır

-2.25  -2.50  3.14  2.68  2.36
-1.95  -2.16  3.14  2.36  2.03
-1.19  -0.98  0.00  0.79  1.11
-0.90  -0.64  0.00  0.46  0.79


B=!!M;
B(2:x-1,2:y-1)=0;

Aşağıdaki matris oluşturuldu

1   1   1   1   1
1   0   0   0   1
1   0   0   0   1
1   1   1   1   1

d=bwdist(B,'chessboard');

Halka indeksleri oluşturmak için satranç tahtası mesafesini kullanarak B mesafe dönüşümünü hesaplar.

0   0   0   0   0
0   1   1   1   0
0   1   1   1   0
0   0   0   0   0               

6 * 7 matris için aşağıdaki matriks olacaktır.

0   0   0   0   0   0   0
0   1   1   1   1   1   0
0   1   2   2   2   1   0
0   1   2   2   2   1   0
0   1   1   1   1   1   0
0   0   0   0   0   0   0   

[~,I]=sortrows([d(:) t(:)]);

leksikografik sıralama ilk önce halka indeksine ve sonra açı sırasına göre (sıralanan öğelerin indeksleri)

    for k=0:max(d(:))
        M(h)=shift(M(h=I(d(I)==k)),R);
    end

ve son olarak her bir halkanın dairesel kayması.


4

Python 3, 292 288 bayt

_=eval
a=input().split()
b,a=int(a[0]),_("".join(a[1:]))[::-1]
c=len(a)
d=len(a[0])
e=range
f="int((i>=j and i+j<c-1)|2*(i>=c/2and i+d>j+c)|3*(i<c/2and i+j<d))"
l=[-1,1,0,0],[0,0,1,-1]
g=lambda x:[[x[i+l[0][_(f)]][j+l[1][_(f)]]for j in e(d)]for i in e(c)]
print(_("g("*b+"a"+")"*b)[::-1])

Yeni satırlar kaldırılmış olarak girdi alır, ancak onu döndürmek için artan sayıdan sonra bir boşluk bırakır.

Açıklama:

Matrisi OP'nin önerisine göre bir dizi eş merkezli halka olarak modellemek yerine, elemanlar tek bir rotasyon sırasında yukarı, aşağı, sağa veya sola hareket eden dört bölgeye ayrılabilir. Uzun değerlendirme dizesinin amacı budur f: Her bir i,jkombinasyonun hangi bölgeye girdiğini belirlemek. Sonra, bunun sonucu iki kez laranır i,jve bir sonraki adımda pozisyonuna dönmesi gereken eleman verilir . Bunların ghepsini yapan ve tek bir adımdan sonra yeni matrisi oluşturan fonksiyon , daha sonra iç içe geçmiş bir fonksiyon çağrısının temsilini içeren bir oluşturulan dizgeyi değerlendirerek tekrar tekrar çağrılır.

Bunu başlangıçta yaptığım zaman, yanlışlıkla matrisin saat yönünün tersine yerine saat yönünde dönmesine neden oldum. Uygun bir düzeltme yapmak yerine, [::-1]dönmeden önce ve sonra matrisi tersine çevirmek için stratejik olarak yerleştirilmiş iki kopya ekledim . Bunlar muhtemelen ~ 280 276 byte'a kadar golf oynayabilir , ancak bunu yapmak için fazla tembelim.

Ayrıca, bu biraz daha uzun bir Python 2 programından test edilmemiş bir hızlı bağlantı noktasıdır, bu yüzden doğru şekilde çalışmazsa beni affet. İşte, yine de Python 2 kodu:

_=eval
a=raw_input().split()
b,a=int(a[0]),_("".join(a[1:]))[::-1]
c=len(a)
d=len(a[0])
e=xrange
f="int((i>=j and i+j<c-1)|2*(i>=c/2and i+d>j+c)|3*(i<c/2and i+j<d))"
l=[-1,1,0,0],[0,0,1,-1]
g=lambda x:[[x[i+l[0][_(f)]][j+l[1][_(f)]]for j in e(d)]for i in e(c)]
print _("g("*b+"a"+")"*b)[::-1]

EDIT: 4 byte orile |iki kez değiştirerek kapalı Golf . andMaalesef yardım edilemez.


PPCG'ye Hoşgeldiniz! Güzel ilk mesaj!
HyperNeutrino,

Aslında komik hikaye - bugün lise marching bandında, herkesin bu soruya benzer eş merkezli dikdörtgen "halkalar" içinde hareket ettiği ve hemen bu cevabı düşündüm.
Aidan F. Pierce

1

Perl, 330 328 bayt

sub f{($r,$m)=@_;$h=@m=@$m;for$s(0..(($w=$#{$m[0]})<--$h?$w:$h)/2-.5){@_=(@{$m[$s]}[@x=$s..($x=$w-$s)],(map$m[$_][$x],@y=1+$s..($y=$h-$s)-1),reverse(@{$m[$y]}[@x]),(map$m[$h-$_][$s],@y));push@_,shift
for 1..$r;@{$m[$s]}[@x]=map shift,@x;$m[$_][$x]=shift for@y;@{$m[$y]}[@x]=reverse map shift,@x;$m[$h-$_][$s]=shift for@y}@$m=@m}

Ideone'da dene .

Ungolfed:

sub f {
    my ($r, $m) = @_;

    my @m = @$m;
    my $h = $#m;
    my $w = @{$m[0]} - 1;
    my $c = (($w < $h ? $w : $h) + 1) / 2 - 1;

    for my $s (0 .. $c) {
        my $x = $w - $s;
        my $y = $h - $s;
        my @x = $s .. $x;
        my @y = $s + 1 .. $y - 1;

        # One circle.
        @_ = (@{$m[$s]}[@x],
              (map { $m[$_][$x] } @y),
              reverse(@{$m[$y]}[@x]),
              (map { $m[$h - $_][$s] } @y));

        # Circular shift.
        push(@_, shift(@_)) for 1 .. $r;

        @{$m[$s]}[@x] = map { shift(@_) } @x;
        $m[$_][$x] = shift(@_) for @y;
        @{$m[$y]}[@x] = reverse(map { shift(@_) } @x);
        $m[$h - $_][$s] = shift(@_) for @y;
    }

    @$m = @m;
}
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.