Ters girinti


63

Kodunuzun tersine girerseniz, kodunuzun daha hızlı çalışabileceğini duydum, böylece derleyici "dalların" en altından bir ağaç tasarım deseni gibi işleyebilir. Bu yardımcı olur çünkü yerçekimi, kodunuzun derlenmesi için gereken zamanı hızlandırır ve veri yapısı verimliliği artar. Java komut dosyasında bir örnek:

            function fib(n) {
        var a = 1, b = 1;
        while (--n > 0) {
    var tmp = a;
    a = b;
    b += tmp;
    if (a === Infinity) {
return "Error!";
    }
        }
        return a;
            }

Ancak bazı nedenlerden dolayı Notepad'in bunu otomatik olarak yapacak bir ayarı yoktur, bu yüzden benim için yapacak bir programa ihtiyacım var.

Açıklama

Gönderimler girdi olarak bir kod pasajı almalı, girintiyi tersine çevirmeli ve ortaya çıkan kodu vermelidir.

Bu, aşağıdaki prosedürle yapılır:

  • Kodu satırlara bölün. Her satır sıfır veya daha fazla boşlukla başlayacaktır (sekme olmayacak).

  • Koddaki tüm benzersiz girinti seviyelerini bulun. Örneğin, yukarıdaki örnek için, bu

    0
    4
    8
    12
    
  • Bu girinti seviyeleri listesinin sırasını ters çevirin ve ters çevrilmiş listeyi orijinal listeyle eşleyin. Bunu kelimelerle açıklamak zor, ama örneğin, benziyor

    0  — 12
    4  — 8
    8  — 4
    12 — 0
    
  • Bu eşlemeyi orijinal koda uygulayın. Örnekte, 0 boşluk girintili bir satır 12 boşluk, girintili 4 boşluk 8 boşluk olacaktı.

Giriş çıkış

İstediğiniz gibi giriş ve çıkış sağlanabilir (STDIN / STDOUT, fonksiyon parametresi / dönüş değeri vb.); Diliniz çok satırlı girişi desteklemiyorsa (veya sadece istemiyorsanız), |karakterleri satırları ayırmak için kullanabilirsiniz .

Girdi yalnızca yazdırılabilir ASCII + yeni satırlarından oluşacak ve boş satır içermeyecek.

Test durumları

Giriş:

function fib(n) {
    var a = 1, b = 1;
        while (--n > 0) {
            var tmp = a;
            a = b;
            b += tmp;
            if (a === Infinity) {
                return "Error!";
            }
        }
    return a;
}

Çıktı: Yukarıdaki örnek kod.

Giriş:

a
  b
  c
d
   e
        f
  g
   h

Çıktı:

        a
   b
   c
        d
  e
f
   g
  h

Giriş:

1
 2
  3
 2
1

Çıktı:

  1
 2
3
 2
  1

Giriş:

  foo

Çıktı:

  foo

21
"JavaScript" değil "Java komut dosyası": /
Optimizer

75
@Optimizer İlk iki paragraf ile mümkün olduğunca çok insanı kızdırma hedefime ulaşıldığını gördüm. ;)
Doorknob

7
1! = Mümkün olduğu kadar çok insan.
İyileştirici

23
@JanDvorak MLA tarzı alıntıları icat eden aynı adamlar bunun iyi bir fikir olduğunu düşünüyor.
Rainbolt

6
Güya, daha hızlı. Bir komite atayalım ve amacını unuturken birkaç yıl bekleyelim.
Conor O'Brien,

Yanıtlar:


10

CJam, 43 39 36 35 bayt

qN/_{_Sm0=#}%___&$_W%er]z{~S*@+>N}%

Bu uzun zamana kadar görünüyor. Yeterince optimizasyon yapmadığımdan eminim !

Nasıl çalışır:

Temel fikir, girdiyi yeni satırda bölmek, her satırdaki satır aralığı sayısını hesaplamak, benzersiz sayıları sıralamak ve almak, bu diziyi kopyalamak ve kopyayı tersine çevirmek, orijinal sıralı sayıları bu iki diziyle çevirmek ve son olarak biçimlendirmektir. Bu bilgiyi kullanarak son dize.

En uzun bölüm, CJam bunu yapmanın kolay bir yoluna sahip olmadığı için her satırda kaç tane öncü boşluk bulunduğunu bulmaktır.

Kod genişletme:

qN/_                                      "Split the string on newline and take copy";
    {_Sm0=#}%                             "Map this code block on the copy";
     _Sm                                  "Copy the string and remove spaces from the copy";
        0=                                "Get first non space character";
          #                               "Gets its index in original string";
             ___                          "Get 3 copies of the above array";
                &$_W%                     "Get unique elements, sort, copy and reverse";
                     er                   "Transliterate unique sorted elements with";
                                          "the unique reverse sorted in the copy";
                       ]z                 "Get array of [row,
                                          " original number of leading spaces,
                                          " required number of leading spaces]";
                         {~S*@+>N}%       "For each above combination";
                          ~S*             " unwrap and get leading space string";
                             @+           " prepend to the row";
                               >          " remove original spaces";
                                N         " put newline";

Ve sorunun özünde. Kodun gerçek bir genişlemesi:

                                          qN/_                                      "Split the string on newline and take copy";
                                {_Sm0=#}%                             "Map this code block on the copy";
                               _Sm                                  "Copy the string and remove spaces from the copy";
                             0=                                "Get first non space character";
                          #                               "Gets its index in original string";
                         ___                          "Get 3 copies of the above array";
                       &$_W%                     "Get unique elements, sort, copy and reverse";
                     er                   "Transliterate unique sorted elements with";
"the unique reverse sorted in the copy";
                ]z                 "Get array of [row,
" original number of leading spaces,
" required number of leading spaces]";
             {~S*@+>N}%       "For each above combination";
          ~S*             " unwrap and get leading space string";
        @+           " prepend to the row";
     >          " remove original spaces";
    N         " put newline";

Martin ve 7 byte Dennis sayesinde 1 byte kurtarıldı

Burada çevrimiçi deneyin


1. {}#bir hata var: bir Tamsayı döndürür, ancak bir Uzun döndürmelidir. İronik olarak, i(tamsayıya döküm) bunu düzeltir. 2. ""#Aynı hatayı olmadığından _Sm0=#, bir bayt daha kısa.
Dennis

@Dennis Evet, böcek garip. Geçici çözüm için teşekkürler!
Doktoru

2
genişlemedeki bu girintiyi okumak çok kolaydır! Tersine çevirmelisin!
DLeh

13

Python 2 - 137 131 bayt

i=raw_input().split('|')
f=lambda s:len(s)-len(s.lstrip())
d=sorted(set(map(f,i)))
for l in i:print' '*d[~d.index(f(l))]+l.lstrip()

İle giriş Alır |yerine \n.

açıklama

İlk üç satır oldukça basittir. Girdideki tüm satırların bir listesini yapın, bir dizgenin ne kadar önde gelen beyaz alana sahip olduğunu söyleyen bir işlev tanımlayın ve işlevin her girdi satırı için yaydığı değerlerin sıralı bir listesini yapın.

Son satır çok daha eğlenceli.

                                 l               # string with the line
                               f(l)              # amount of leading whitespace
                       d.index(f(l))             # where it is in list of whitespace amounts
                      ~d.index(f(l))             # bitwise NOT (~n == -(n+1))
                    d[~d.index(f(l))]            # index into the list (negative = from end)
           print' '*d[~d.index(f(l))]            # print that many spaces...
           print' '*d[~d.index(f(l))]+l.lstrip() # plus everything after leading whitespace
for l in i:print' '*d[~d.index(f(l))]+l.lstrip() # do the above for every line


@frya thanks :)
undergroundmonorail

1
Bunların hepsi python 3'te iyi görünüyor, ki bu da 2 bayttan tasarruf etmeli ( ()4 tasarruf için 2 raw_
ödeyiniz

1
f(s)for s in iolmalı map(f,i).
feersum

1
Bir sihir parçası: d=[];d+=set(L)daha kısa bir versiyonudur d=sorted(set(L)).
xnor

7

JavaScript, ES6, 113 103 101 bayt

En azından biraz daha golf oynayabileceğinden eminim ama işte gidiyor.

Python'u yenecek bir 101 bayt JS çözümü olacağını asla düşünmezdim!

f=a=>(b=c=[...Set(a.match(r=/^ */gm).sort())],c.map((x,i)=>b[x]=c.slice(~i)[0]),a.replace(r,x=>b[x]))

Bu fgiriş dizesi ile çağrılabilecek bir yöntem yaratır . En son Firefox'unuz varsa, şablon dizeleriniz vardır ve bu gibi yöntemleri çağırabilirsiniz

f(`a
  b
  c
d
   e
        f
  g
   h`)

Aksi takdirde, aynı şekilde

f("a\n\
  b\n\
  c\n\
d\n\
   e\n\
        f\n\
  g\n\
   h")

veya aşağıdaki pasajı deneyin:

g=_=>O.textContent=f(D.value)

f=a=>(b=c=[...Set(a.match(r=/^ */gm).sort())],c.map((x,i)=>b[x]=c.slice(~i)[0]),a.replace(r,x=>b[x]))
<textarea id=D></textarea><button id=B onclick=g()>Inverse!</button>
<pre id=O></pre>


Regex'i iki kez kullanıldığı için değişken olarak saklayarak ( \sboşluk karakteriyle değiştirebilmelisiniz ) ve xdeğiştirme işlevindeki parantezleri kaldırarak bir bayt baytını kaydedebilirsiniz .
NinjaBearMonkey

@hsl gee, teşekkürler! Neden yazdığımı bile bilmiyorum (x): /
Doktoru

Her iki gerekmez bve cdeğil mi? Yine de aynı diziye başvuruyorlar.
Neil

5

Ruby, 63 bayt

->s{l=s.scan(r=/^ */).uniq.sort;s.gsub r,l.zip(l.reverse).to_h}

Bu, bir dize alan ve döndüren adsız bir işlevi tanımlar. Ekleyerek ["string here"]veya bir değişkene atayarak ve sonra bu değişkeni çağırarak arayabilirsiniz .

Nasıl çalışır: daha sonra kullanılmak üzere s.scan(r=/^ */)regex içine alan bütün önde gelen alanların ve mağazaların bir listesini verir r. uniqçoğaltmaları ortadan kaldırır. sort... çeşitler.

Şimdi sonuna atlayın, l.zip(l.reverse)yerine koymak istediğimiz bir çift çift verir. to_hBunu bir karma haline getirir, çiftleri anahtar-değer çiftleri olarak yorumlar.

Şimdi s.gsubregex'in tüm eşleşmelerinin (tüm ön boşlukların) yerini değiştirmeyi bulmak için bu karmayı bir tarama tablosu olarak kullanarak değiştirdik.



2

Japt -R , 27 bayt

·
mâ\S
Vâ n
Ëx2 iSpWg~WbVgE

Çevrimiçi deneyin!

Ambalajsız ve Nasıl Çalışır?

Input: U = multiline string

qR    Split by newline and implicit assign to U

mâ\S
m     Map over U...
 â\S    .search(/\S/); first index of non-whitespace char
      Implicit assign to V (V = array of indentations)

Vâ n  Take unique elements of V, sort, and implicit assign to W

mDEF{Dx2 iSpWg~WbVgE
mDEF{                 Map over U...
     Dx2                Trim left
         iSp            Indent by this many spaces...
                 VgE      Find the current indentation stored in V
               Wb         Find its index on W
            Wg~           Take the opposite element on W

-R    Join with newline

Gerçekten nasıl çalışıyor

                 Input: U = multiline string

                 qR    Split by newline and implicit assign to U

                 mâ\S
                 m     Map over U...
               â\S    .search(/\S/); first index of non-whitespace char
         Implicit assign to V (V = array of indentations)

                 Vâ n  Take unique elements of V, sort, and implicit assign to W

                 mDEF{Dx2 iSpWg~WbVgE
                 mDEF{                 Map over U...
            Dx2                Trim left
      iSp            Indent by this many spaces...
VgE      Find the current indentation stored in V
 Wb         Find its index on W
     Wg~           Take the opposite element on W

                 -R    Join with newline

1

Scala, 176 171

def g(n:String)={val a=n.split('|').map(a=>a.prefixLength(' '==)->a)
(""/:a){case(s,(l,p))=>val b=a.unzip._1.distinct.sorted
s+" "*b.reverse(b.indexOf(l))+p.drop(l)+'\n'}}

Sonunda fazladan bir yeni satır ekleyecektir. Satırın sonundaki boşlukları korumak zorunda kalmazsam, 167’ye ulaştırabilirim:

def t(n:String)={val a=n.split('|').map(a=>a.prefixLength(' '==)->a.trim)
(""/:a){(s,l)=>val b=a.unzip._1.distinct.sorted
s+" "*b.reverse(b.indexOf(l._1))+l._2+'\n'}}

Ungolfed:

      def reverseIndent(inString: String): String = {
    val lines = inString.split('\n')
    val linesByPrefixLength = lines.map { line =>
  line.prefixLength(char => char == ' ') -> line
    }
    val distinctSortedPrefixLengths = linesByPrefixLength.map(_._1).distinct.sorted
    val reversedPrefixes = distinctSortedPrefixLengths.reverse
    linesByPrefixLength.foldLeft("") { case (string, (prefixLength, line)) =>
  val newPrefixLength = reversedPrefixes(distinctSortedPrefixLengths.indexOf(prefixLength))
  val nextLinePrefix = " " * newPrefixLength
  string + nextLinePrefix + line.substring(prefixLength) + '\n'
    }
      }

1

PowerShell , 112 bayt

$x=@($args|sls '(?m)^ *'-a|% m*|% v*|sort -u)
[regex]::Replace($args,'(?m)^ *',{$x[-1-$x.IndexOf($args.Value)]})

Çevrimiçi deneyin!

Daha az golf oynadı:

$xIdents=@($args|select-string '(?m)^ *'-AllMatches|% matches|% value|sort -unique) # get a sorted set of indentations
[regex]::Replace($args,'(?m)^ *',{$xIdents[-1-$xIdents.IndexOf($args.Value)]})    # replace each indentation with opposite one

0

Haskell, 116

import Data.List
f s|l<-map(span(==' '))$lines s=unlines[k++b|(a,b)<-l,(k,r)<-reverse>>=zip$sort$nub$map fst l,r==a]

0

PHP - 173 bayt

Geliştirilmemiş kod $vdeğişkende saklanmalıdır :

<?php $f='preg_replace';$f($p='#^ *#me','$i[]='.$s='strlen("$0")',$v);$a=$b=array_unique($i);sort($a);rsort($b);echo$f($p,'str_repeat(" ",array_combine($a,$b)['.$s.'])',$v);

İşte ungolfed ve yorumlanan versiyonu:

<?php
// Get the level of indentation for each line
$preg_replace = 'preg_replace';
$pattern = '#^ *#me';
$strlen = 'strlen("$0")';
$preg_replace($pattern, '$indentationLevelsOldList[] = '. $strlen, $value);

// Create an array associating the old level of indentation with the new expected one
$sortedArray = array_unique($indentationLevelsOldList);
$reverseSortedArray = $sortedArray;

sort($sortedArray);
rsort($reverseSortedArray);

$indentationLevelsNewList = array_combine($sortedArray, $reverseSortedArray);

// Print the correctly indented code
echo $preg_replace($pattern, 'str_repeat(" ", $indentationLevelsNewList['. $strlen .'])', $value);

Muhtemelen hiç bu kadar kirli bir şey yazmamıştım. Utandım.


0

JavaScript, 351

var i=0;var a=$("#i").html().split("\n");var b=[];for(;i<a.length;i++){j=a[i].match(/\s*/)[0];if(b.indexOf(j)<0){b.push(j);}}b.sort(function(a,b){return a - b;});var c=b.slice().reverse();var d="";for(i=0;i<a.length;i++){d+=a[i].replace(/\s*/,c[b.indexOf(a[i].match(/\s*/)[0])])+"\n";j=a[i].search(/\S/);if(b.indexOf(j)<0){b.push(j);}}$("#i").html(d);

Ungolfed versiyonu:

var i = 0;
var a = $("#i").html().split("\n");
var b = [];
for (; i < a.length; i++) {
  j = a[i].match(/\s*/)[0];
  if (b.indexOf(j) < 0) {
    b.push(j);
  }
}
b.sort(function(a, b) {
  return a - b;
});
var c = b.slice().reverse();
var d = "";
for (i = 0; i < a.length; i++) {
  d += a[i].replace(/\s*/, c[b.indexOf(a[i].match(/\s*/)[0])]) + "\n";
  j = a[i].search(/\S/);
  if (b.indexOf(j) < 0) {
    b.push(j);
  }
}
$("#i").html(d);

Test yapmak


0

Perl 5, 112

111 + 1 -n( -Eücretsiz)

@{$.[$.]}=/( *)(.*)/;++$_{$1}}{map$_{$_[$#_-$_]}=$_[$_],0..(@_=sort keys%_);say$_{$.[$_][0]}.$.[$_][1]for 0..$.

Daha az vuruşla yapılabildiğinden eminim, ama şu anda nasıl olduğunu bilmiyorum.

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.