Bir dize kare oymak


21

Bugünkü zorluğunuz çok satırlı bir dizi almak ve sol üst köşeyi içeren dizede bulunan en büyük kareyi çıkarmaktır.

Kare bir dize şudur:

  • Her satırda aynı sayıda karakter var
  • Her satırdaki karakter sayısı, satır sayısına eşittir.

Aşağıdaki olası giriş dizesini göz önünde bulundurun:

abcde
fgh
asdf
foobar

aOndan alabileceğiniz en büyük kare, ilk karakteri içeren ( en üstteki köşedeki) şudur:

abc
fgh
asd

İkinci satır yeterince uzun olmadığından 4 kenar uzunluğunda bir kare olamaz. Şimdi bu potansiyel girişi düşünün:

a
bcd
edf
ghi

Buradaki en büyük meydan sadece a. Dipte oluşan 3x3 kare ilk karakteri içermiyor ve sayılmıyor.

İşte birkaç test vakası:

a

a

abc
def
gh

ab
de

ab
cd

ab
cd

abcde
fghij
klm
no

abc
fgh
klm

a
b

a

Seçtiğiniz LF, CR veya CRLF ile sınırlandırılmış olarak girmeniz gerekebilir.

Yeni satır karakterleri, satır uzunluğunun bir parçası olarak kabul edilmez.

Girişte ek bir satır sayılmayan takip eden bir yeni satır olmanız veya olmamanız gerekebilir.

Giriş bir dize veya 1D karakter dizisidir; dizelerin listesi değildir.

Girişin boş olmadığını ve tüm satırların boş olmadığını ve boşluklar ve yeni satırlar (satır sınırlayıcı için) dahil ancak sekmeler dahil olmak üzere yalnızca yazdırılabilir ASCII içerdiğini varsayabilirsiniz.

Bu , en az bayt kazanıyor!



5
İlginç bir meydan okuma için +1, katı G / Ç için -1
Dennis

@Dennis her çözümün kullanılması .split('\n')gerekmediğinden, neden bazılarının ücretsiz olarak alacağını anlamıyorum.
Pavel

2
(Sadece) sıkıcı kazan plakası için bayt eklemek zorunda değil. Bazı yaklaşımlar (örneğin özyinelemeli fonksiyonlar), ön işleme veya son işlem varsa, tamamen pratik değildir.
Dennis

@Dennis Ben böyle düşünmemiştim. Sence şimdi değiştirmem mi gerekiyor yoksa çok mu geç?
Pavel

Yanıtlar:


5

Brachylog , 11 bayt

ṇ⊇ᵐẹa₀ṁcᵐ~ṇ

Çevrimiçi deneyin!

açıklama

ṇ             Split on linebreaks
 ⊇ᵐ           Take a subset of each line
   ẹ          Split the lines into list of chars
    a₀        Take a prefix of this list of lists of chars
      ṁ       It is a square matrix
       cᵐ     Concatenate the list of chars back into strings
         ~ṇ   Join the strings with linebreaks

En kısa çözümde iyi bir iş (şimdiye kadar), Brachylog kesinlikle kareleri seviyor, değil mi?
Pavel

@Pavel Yerleşik gerçekten oldukça kullanışlı!
17'de

7

Kabuğu , 13 bayt

►oΛ≈S+TzṀ↑Nḣ¶

Çevrimiçi deneyin!

açıklama

►oΛ≈S+TzṀ↑Nḣ¶  Implicit input, say "ab\nc".
            ¶  Split at newlines: ["ab","c"]
           ḣ   Take prefixes: [["ab"],["ab","c"]]
       z  N    Zip with [1,2,3..
        Ṁ↑     by taking that many characters from each row: [["a"],["ab","c"]]
►o             Find rightmost element that satisfies this:
  Λ            all strings in
    S+T        the list concatenated to its transpose
   ≈           have the same length: ["a"]
               Implicitly print separated by newlines.

1
Bu bir programlama dili nasıl olsa bile - belirsiz bazı unicode karakterleri yapıştırdınız! ;)
şalgam

1
@Petar Belirli bir görevi yerine getirmek için olabildiğince az byte kullanmak üzere tasarlanmış golf dilleri dünyasına hoş geldiniz. Bunun bir kısmı özel bir kod sayfasına sahip olmaktır, böylece normal yazdırılabilir ASCII yerine her bir bayt için bir karakter bulunur. Ancak endişelenmeyin, daha okunaklı golf dilleri de var; Mesela MATL girişim [/ utanmaz kişisel tanıtım]
Sanchises

5

GNU sed , 106 + 1 94 + 2 = 96 bayt

-rzBayraklar için +2 bayt . Burada @ve #burada gösterilen yazdırılamaz karakterleri NUL ve BEL kullanır . Bir xxd dökümü için aşağıya bakın.

Beni yolda izlediği için @ seshoumara'ya teşekkürler -z.

s/^/@/gm
s/.*/#&\n/
:B
s/@(.)/\1@/mg
s/#(.+\n)/\1#/m
/#.*@./M!b
/@\n.*#/!bB
:
s/@[^\n]*|#.*//g

Çevrimiçi deneyin!

açıklama

Bu, metne iki imleç ekleyerek çalışır - biri satırlar arasında, diğeri sütunlar üzerinde adım adım. İmleçler sırasıyla NUL (0x00) ve BEL (0x07) ile temsil edilir, ancak aşağıdaki örneklerde @ve kullanacağım #. Diyelim ki bu girdi bizde:

abcde
fgh
asdf
foobar

BEL imleci 0. Kolondan önce ve BEL imleci 0. Satırdan önce yerleştirilir (burada sütunları okunaklı olması için hizaya getirdim;

#@abcde
 @fgh
 @asdf
 @foobar

Döngüde, imleçler sırasıyla bir karakter sağa ve bir satır aşağı taşınır:

 a@bcde
#f@gh
 a@sdf
 f@oobar
 ab@cde
 fg@h
#as@df
 fo@obar
 abc@de
 fgh@
 asd@f
#foo@bar

Her yinelemeden sonra iki koşulu kontrol eder:

  1. Satır imlecinin bulunduğu satırda bir sütun imleci var mı ve sütun imleci sağa hareket edebilir mi?
  2. Çizgi imlecinden önceki satırlarda, her sütun imleci sağa hareket edebilir mi?

Her iki koşul da yanlışsa, döngü sona erer. Komut @, her satırdaki her şeyi #ve kalıp uzayındaki her şeyi silerek bitirilir .

xxd dökümü

00000000: 732f 5e2f 002f 676d 0a73 2f2e 2a2f 0726  s/^/./gm.s/.*/.&
00000010: 5c6e 2f0a 3a42 0a73 2f00 282e 292f 5c31  \n/.:B.s/.(.)/\1
00000020: 002f 6d67 0a73 2f07 282e 2b5c 6e29 2f5c  ./mg.s/.(.+\n)/\
00000030: 3107 2f6d 0a2f 072e 2a00 2e2f 4d21 620a  1./m./..*../M!b.
00000040: 2f00 5c6e 2e2a 072f 2162 420a 3a0a 732f  /.\n.*./!bB.:.s/
00000050: 005b 5e5c 6e5d 2a7c 072e 2a2f 2f67       .[^\n]*|..*//g

İlk döngü olan A'yı kaldırabilirsiniz, çünkü deyim girdiyi bir dizge olarak okumak zorunda kaldığınızı söyler, böylece "line1 \ nline2 \ nline3" vb. Bu sayının 100'ün altına düşmesi gerekir :)
seshoumara

@seshoumara Diğer cevaplar yapmak line1\nline2\nline3nerede \nolduğunu \x5C\x6E? Hangi?
Jordan

Bana bir link verir misin? (Herhangi bir cevabın alt kısmındaki "paylaş" seçeneğini tıklayın.) Veya bana bir TiO'da ne demek istediğinizi gösterin? Tüm Python ve PHP cevaplarında gördüğüm \nyeni satır karakteri ( \x0A, değil \x5C\x6E) olarak yorumlanır ve sed satırının yeni satır karakterleriyle tek satır olarak giriş yapmasını sağlayacak bir yol bulamıyorum.
Jordan

@seshoumara Hah, neyse, ben sadece -zbayrağı hatırladım . Teşekkürler!
Ürdün

4

Python 2 , 81 bayt

l=input().split('\n')
i=0
while zip(*l[:i+1])[i:]:i+=1
for x in l[:i]:print x[:i]

Çevrimiçi deneyin!


İlginç bir yöntem, ancak 2 bayt daha uzun.

Python 2 , 83 bayt

l=input().split('\n')
while len(zip(*l))<len(l):l.pop()
for x in l:print x[:len(l)]

Çevrimiçi deneyin!


1
Does not inputsadece bir satır okumak?
Pavel

@Pavel, çevrimiçi örneğe bakarsanız, girişi bir satırlık bir dize tutmak için açık yeni satır karakterleri kullandığını görebilirsiniz. Muhtemelen bu yöntemi tercih etmek, çünkü raw_input()daha fazla bayt ekleyecektir.
Xavier Dass,

4

JavaScript (ES6), 77 bayt

f=(s,i=1,m=s.match(`^${`(.{${i}}).*
`.repeat(i)}`))=>m?f(s,i+1)||m.slice(1):0

Hiçbiri bulunamayana kadar daha büyük ve daha büyük kareler aramak için tekrarlı olarak düzenli ifade kullanır.

Düzenli ifade 3x3 kare için bu olurdu:

^(.{3}).*
(.{3}).*
(.{3}).*

Girişin yeni bir satırla bitmesi bekleniyor ve çıkış bir liste.

Açıklama:

f = (s,                                            //input
     i = 1,                                        //start searching for a 1x1 square
     m = s.match(`^${`(.{${i}}).*\n`.repeat(i)}`)  //match on the regex
    )=>
    m ? f(s, i+1)                   //if there's a match, recurse on the next-sized square
        || m.slice(1) :             //if there's not a next-sized square, return the match
        0                           //no match for this square, so stop recursing

Pasaj:




3

R , 84 83 81 76 bayt

-5 bayt Dennis'in yaklaşımını tasvir ediyorsum

cat(substr(x<-readLines(),1,m<-sum(cummin(nchar(x))>=seq(x)))[1:m],sep='\n')

Çevrimiçi deneyin!

stdin'den okur, sonunda yeni bir satır olmadan stdout'a yazdırır.

Biraz ungolfed:

x <- readLines()                    # read in input one line at a time;
                                    # saved as a vector of strings
minChar <- cummin(nchar(x))         # rolling minimum of all line lengths
lineNum <- seq(x)                   # line number
mins <- minChar>=lineNum            # the min between the line number and the line lengths
m <- sum(mins)                      # the sum of those is the size of the square
cat(substr(x,1,m)[1:m],sep='\n')    # print the first m characters of the first m lines,
                                    # and join with newlines


3

C (gcc) , 162 159 151 147 144 142 142 bayt

Burada golf oynamak için bazı vuruşlar olmalı ...

i,l=9;char*p,s[9][8];main(t){for(p=s;~(*p=getchar());)p=*p<32?*p=0,l=(t=strlen(s+i))<l?t:l,s[++i]:p+1;for(i=0;i<l;puts(s+i++))s[i][l]=0;}

Çevrimiçi deneyin!


Can !=-1olmak >-1veya yok getchar()eksi olandan çıkış değerleri daha küçük? Olabilir +1mi?
Jonathan Frech

Potansiyel 158 bayt .
Jonathan Frech

@ JonathanFrech ~eksi bir tespit etmek için kullanabilirsiniz .
cleblanc

1
@RickHitchcock En son golf versiyonunda çalışıyor gibi görünüyor.
cleblanc

2

Jöle , 15 bayt

L€«\‘>Jx@Z
ỴÇÇY

Çevrimiçi deneyin!

Nasıl çalışır

ỴÇÇY        Main link. Argument: s (string)

Ỵ           Split s at linefeeds, yielding a string array.
 Ç          Apply the helper link.
  Ç         Apply the helper link again.
   Y        Join, separating by linefeeds.


L€«\‘>Jx@Z  Helper link. Argument: A (string array/2D character array)

L€          Compute the length of each row/line.
  «\        Take the cumulative minimum.
    ‘       Increment each minimum.
      J     Indices; yield [1, ..., len(A)].
     >      Perform elementwise comparison. If the output should have n lines, this
            yields an array of n ones and len(A)-n zeroes.
         Z  Zip/transpose A.
       x@   For each string t in the result to the right, repeat its characters as
            many times as indicated in the result to the left, discarding all but
            the first n characters.

2

Java 8, 150 bayt

s->{String q[]=s.split("\n"),r="";int l=q[0].length(),i=0,t;for(;i<l;l=t<l?t:l)t=q[i++].length();for(i=0;i<l;)r+=q[i++].substring(0,l)+"\n";return r;}

Açıklama:

Burada dene.

s->{                          // Method with String as both parameter and return-type 
  String q[]=s.split("\n"),   //  Split the input on new-lines, and put it in an array
         r="";                //  Result-String, starting empty
  int l=q[0].length(),        //  Length of the lines, starting at the length of line 1
      i=0,                    //  Index-integer, starting at 0
      t;                      //  Temp integer
  for(;i<l;                   //  Loop (1) from 0 to `l` (exclusive)
      l=t<l?                  //    After every iteration: if `t` is smaller than `l`:
         t                    //     Change `l` to `t`
        :                     //    Else:
         l)                   //     Leave `l` the same
    t=q[i++].length();        //   Set `t` to the length of the current line
                              //  End of loop (1) (implicit / single-line body)
  for(i=0;i<l;                //  Loop (2) from 0 to `l` (the determined square dimension)
    r+=                       //   Append the result-String with:
       q[i++].substring(0,l)  //    The current row chopped at `l-1`
       +"\n"                  //    + a new-line
  );                          //  End of loop (2)
  return r;                   //  Return the result-String
}                             // End of method

2

MATL , 33 bayt

10-~ft1)wdhqY<tn:vX<X>:GYbowt3$)c

Çevrimiçi deneyin!

Benim spidey hissim bana muhtemelen daha kısa bir yol olduğunu söylüyor ( Yboen baştan bir şey düşünüyorum ) ... Sonunda yeni bir satır gerektirir. (Not: Bunu biraz fazla geliştirdim, çünkü boş satırları da kaldıracağım, ki bu gerekli değil. Bayt sayısını azaltıp azaltamayacağımı göreceğim, çünkü kod golfünde bir özellik değil, bir hata)


1
@Pavel Guiseppe başka bir sürüme atıfta bulunuyordu, çünkü geri aldığım bir hata vardı.
Sanchises,



1

JavaScript (ES6), 95 bayt

f=
s=>(g=s=>s.slice(0,a.findIndex((e,i)=>a.some((s,j)=>j<=i&!s[i]))))(a=s.split`
`).map(g).join`
`
<textarea oninput=o.textContent=f(this.value+`\n`)></textarea><pre id=o>

Girişte izleyen bir yeni satır gerektirir.



1

APL (Dyalog) , 25 bayt *

Tam önek işlevi. Bir matris döndürür.

(↑↑⍨2⍴(⌊/≢,≢¨))⎕AV[3]∘≠⊆⊢

Çevrimiçi deneyin!

Gerçekten iki bağımsız fonksiyonun tepesinde, yani ⎕AV[3]∘≠⊆⊢garip girdi formatıyla ↑↑⍨2⍴(⌊/≢,≢¨)ilgileniyor ve asıl ilginç işi yapıyor.

⎕AV[3]∘≠ LF'den farkı (üçüncü öğenin LF'den A tomik V'in - karakter seti)

 bölümler (selefinden daha büyük değerlerde başlayan ve 0'da düşen alt diziler)

 argüman

(...)  Aşağıdaki taktik işlevini uygulayın:

2⍴(...)  Aşağıdaki uzunluğu 2'ye yeniden şekillendirin:

  ⌊/ minimum

   dizelerin sayısı

  , bunu takiben

  ≢¨ Her dizideki karakter sayısı

↑⍨ o kadar satır ve sütun al

 Bir matris oluşturmak için diziler birbirine karıştı (boşluklarla doldurma)


* In Klasik ⎕ML( M igration L evel) 3(çok sistemlerde varsayılan) ve ikame için ve en soldan için . Tio!


Dyalog Classic'te aynı uzunluktaysa, bunun Dyalog Classic olduğunu ve dipnotu kullanmadığını söyleyebilirsiniz.
Pavel

@Pavel Her ikisi de Klasik ve ⎕ML←3kullanımdan kaldırıldı, bu yüzden dili normalde göründüğü gibi göstermek istiyorum. Aslında, neredeyse tüm Dyalog APL çözümleri, sadece karakter yerine bayt saydığımız için Klasik varsaymaktadır, ancak Unicode sürümü bile 256 karakterden daha azına anlam atamaktadır.
Ad

1

PHP, 123 bayt

for(;preg_match("#^(\S{".++$i."}.*
){"."$i}#",$s="$argv[1]
"););while($k<$i-1)echo substr(split("
",$s)[+$k++],0,$i-1),"
";

PHP 5.4, 5.5 veya 5.6 gerektirir. Daha sonra PHP splitile değiştirin explode.

Çevrimiçi olarak çalıştırın php -nr '<code> '<string>'
veya deneyin . (Uygun bir PHP sürümü seçtiğinizden emin olun!)



1

Perl 5, 60 +5 (-0777p) bayt

$.++while/^(.{$.}.*
){$.}/;$_=join"
",(/.{$.}/gm)[0..--$.-1]

Çevrimiçi deneyin

  • Son girdi satırı çıktıya ait olması durumunda yeni bir satırla bitmelidir.
  • Ardışık iki yeni hat olması durumunda -00 seçeneği -0777 ile değiştirilebilir.

İki ardışık yeni hat mümkündür, bu yüzden ihtiyacınız olacak -0777. Her neyse, ne yap -00ve ne yap -0777.
Pavel

-0kayıt ayırıcıyı sekizli formatta belirtmek, ayırıcıyı belirtmemek için 777özel bir değerdir, bu nedenle tüm dosya okunur, 0"paragraf modunu" belirtmek için başka bir özel değerdir, ayırıcı ardışık 1'den fazla yeni
satırdır

1

Perl 6 , 158 140 bayt

my$c;for ^(my@b=lines).elems {any(@b.head(++$c).map({.substr(0,$c).chars <$c}))&&$c--&&last;};say @b.head($c).map({.substr(0,$c)}).join("
")

Çevrimiçi deneyin!

İlk Perl 6 cevabım için yaşasın. Bunu biraz daha golf yapabilir miyim görmek için bazı komut satırı seçenekleri ile oynayacağım. Bayt tasarrufu tüm yardım açığız!


1

Scala , 201 bayt

type S=String
def c(s:S):S={val? =s split "\n"
var(z,q:Seq[S])=(Seq(?size,?(0).size).min,Nil)
while(1<2){?map(i=>{if(i.size>=z)q=q:+i.take(z)
if(q.size==z)return q mkString "\n"})
q=Nil;z-=1}
return""}

Çevrimiçi deneyin!

İlk defa bu dilde golf oynamak, belki de en iyisi değil.

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.