Yol Uzunluk Kodlaması


21

Amerika Birleşik Devletleri'nde , bir yol üzerindeki trafiğin iki karşıt yönü, geçmeye izin veriliyorsa kesik sarı bir çizgi ve geçmeye izin verilmediği takdirde iki kesintisiz sarı çizgi ile ayrılır.

yol çizgisi kuralları grafiği

(Bu tarafın geçmesine izin vermek için yalnızca bir taraf kesilebilir ve sarı çizgiler merkez veya tersine çevrilebilir şerit gibi başka şeyler anlamına gelebilir, ancak bu durumların hiçbiriyle ilgilenmiyoruz.)

Bir de götüren bir program yazın sayı-uzunluk kodlanmış dizesi Piçin geçen ve Niçin hiçbir geçerken , ve buna karşılık gelen yolun bir ASCII versiyonunu yazdırır. Orta çizgi hariç, yol her zaman aşağıdaki örneklerden kolayca çıkarılabilen aynı desene sahiptir.

Her birinden önce Pve Ngiriş dizesinde pozitif bir ondalık sayı olacaktır . Bu sayı , yolun o andaki bölümünün geçen veya geçen bölgesinin uzunluğunu tanımlar .

Örnekler

Bir girdi, geçiş yolu olmayan12N 12 sütun üretecektir (tümü merkez çizgisi ):=

____________


============

____________

Bir girdi, 12P12 sütun geçiş yolu üretecektir (merkez hat - tekrarı):

____________


- - - - - - 

____________

Geçiş ve geçiş hiçbir zaman birleştirilemez, örneğin 4N4P9N7P1N1P2N2P:

______________________________


====- - =========- - - -=-==- 

______________________________

Bunlar 4 tane geçmeyen sütun, sonra 4 tane geçiyor , sonra 9 tane geçmiyor vb.

Bir geçiş bölgesinin her zaman -bir boşlukla ( ) değil, en soldaki çizgi ile ( ) başladığını unutmayın . Bu gereklidir.

ayrıntılar

  • Giriş hiçbir zaman üst üste iki Nbölgeye veya iki Pbölgeye sahip olmaz. örneğin 4P5Pasla gerçekleşmeyecek.
  • Olumlu bir numara olmadan harfleri desteklemenize gerek yoktur. Düz Pher zaman olacak 1P, düz Nher zaman olacak 1N.
  • Yolun son sütununun ötesine geçmedikleri sürece takip eden boşluklar olabilir. İsteğe bağlı bir izleyen yeni satır olabilir.
  • Bir program yerine, çalışma uzunluğu kodlanmış dizgisini alan ve ASCII yolunu basan veya döndüren bir işlev yazabilirsiniz.
  • Herhangi bir standart şekilde girdi alır (stdin, komut satırı, function arg).

Bayt cinsinden en kısa kod kazanır. Tiebreaker daha önce yayınlandı.


Yol asimetrik mi olmalı yoksa hattın her iki tarafına da 4 yol boşluğu bırakılmasına izin veriliyor mu?
orlp

@orlp Yolun 5 satırdan daha geniş olup olmadığını soruyorsanız, hayır. Boşluk karakterlerinin orta çizginin üstündeki veya altındaki boş satırlara yerleştirilip yerleştirilemeyeceğini soruyorsanız, ayrıntı mermi 3 ile tutuldukları sürece evet
Calvin's Hobbies

Örnek olarak soracağım, bunlardan biri geçerli bir çıktı mı? gist.github.com/orlp/0e0eae16d6e1fcda5e9b
orlp

@orlp Hiçbiri değil.
Calvin'in Hobileri

Yanıtlar:


5

CJam, 38 bayt

"_  - _":N3'=t:P;q~]2/e~z'
*"--"/"- "*

Nasıl çalışır

Biz ilk değişkenlere doğru yol sütununu atamak Nve Pardından basitçe giriş dizesini değerlendirir. Bu, bir çift uzunluk ve istif üzerinde sütun bırakır. Onları gruplandırırız, tam sütunlar elde etmek için bir RLD çalıştırırız, birleştiririz ve sonunda sürekli --olarak dönüştürürüz -.

:_  - _":N                    e# This is the no passing column. We assign it to N
          3'=t:P              e# Replace the '-' in N with '=" and assign it to P
                q~]2/         e# Read the input, evaluate it and then group it in pairs
                     e~       e# Run a run-length-decoder on the pairs
                       z'
*                             e# Transpose and join with new lines.
 "--"/                        e# Split on two continuous occurrence of -
      "- "*                   e# Join by an alternate "- "

Burada çevrimiçi deneyin


6

JavaScript (ES6), 114

Kullanılması şablon dizeleri , 5 linefeeds sayılmalıdır edilir önemlidir.

f=s=>(b=(s=s.replace(/(\d+)(.)/g,(x,n,b)=>(b<'P'?'=':'- ').repeat(n).slice(0,n))).replace(/./g,'_'))+`


${s}

`+b

5

rs , 252 karakter

Bu sayılmayabilir, çünkü yakınsama operatörünü bir saat önce Martin Büttner Retina'nın bir kopyası olarak ekledim ... Yine de rekabet etmek için burada değilim. Bunun için regex tabanlı bir çözüm bulmak sadece eğlenceli.

(\d+\D)/#\1
+(\d*)#(?:(((((((((9)|8)|7)|6)|5)|4)|3)|2)|1)|0)(?=\d*\D)/\1\1\1\1\1\1\1\1\1\1\2\3\4\5\6\7\8\9\10#
\d(?=\d*#N)/=
(^|(?<=\D))\d(?=\d*#P)/-
+(?<=-)\d\d(?=\d*#P)/ -
(?<=-)\d(?=\d*#P)/ 
#\D/
((?:(=|-| ))+)/A\1\n\n\n\1\n\nA\1\n
+(A_*)(.)/\1_
A/

Yıllar boyunca Programlama Dilleri'nin Martin Retina cevabını 2. satırda aldım .

açıklama

(\d+\D)/#\1
+(\d*)#(?:(((((((((9)|8)|7)|6)|5)|4)|3)|2)|1)|0)(?=\d*\D)/\1\1\1\1\1\1\1\1\1\1\2\3\4\5\6\7\8\9\10#

Bu çok sihir yapar. Daha fazla bilgi için yukarıda bağladığım cevaba bakınız.

Temel olarak, girdiyle 4N4P9N7P1N1P2N2P, sonuç şu olacaktır:

4444#N4444#P999999999#N7777777#P1#N1#P22#N22#P

Sonraki:

\d(?=\d*#N)/=

Bu, geçiş yapmayan sembolden (N) önceki sayıları eşit işaretlerle değiştirir. Önceki giriş ile sonuç:

====#N4444#P=========#N7777777#P=#N1#P==#N22#P

Bu:

(^|(?<=\D))\d(?=\d*#P)/-

bir geçiş sembolünden (P) önceki ilk sayıyı ilk tire ile değiştirir. Sonuç:

====#N-444#P=========#N-777777#P=#N-#P==#N-2#P

Sonraki iki satır aynı düzende devam eder:

+(?<=-)\d\d(?=\d*#P)/ -
(?<=-)\d(?=\d*#P)/ 

İlk satır, çizginin geri kalanını çizgi-boşluğu deseni ile değiştirir. İkincisi, tek bir sayıyı ele alır; Son tire ve ardından tek bir tamsayı (örneğin -5) bir tire-boşluk ( -) ile değiştirir. Şimdi, çıktı:

====#N- - #P=========#N- - - -#P=#N-#P==#N- #P

Şimdi işler yerinden düşmeye başladı. Bir sonraki satır:

#\D/

sadece #Nve kaldırır #P.

((?:(=|-| ))+)/A\1\n\n\n\1\n\nA\1\n
+(A_*)(.)/\1_

Aşağıdakileri yapmak için alt ve üstteki alt çizgileri ayarlayın:

A______________________________


====- - =========- - - -=-==- 

A______________________________

Son olarak A:

A/

2

Haskell, 165 bayt

k 'N'="="
k _="- "
d c=c>'/'&&c<':'
p[]=[]
p s=take(read$takeWhile d s)(cycle$k a)++p r where(a:r)=dropWhile d s
f s=unlines[q,"\n",p s,"",q]where q=map(\x->'_')$p s

Örnek çalışma ( fbir dize döndürür, bu nedenle daha iyi görüntülemek için yazdırın):

*Main> putStr $ f "4N4P9N7P1N1P2N2P"
______________________________


====- - =========- - - -=-==- 

______________________________

Nasıl çalışır: pgiriş satırını tekrar tekrar ayrıştırarak ve arama işlevinin bulduğu belirli sembol sayısını birleştirerek orta satırı döndürür k. Ana işlev f, üst çizgiden (orta çizginin her yerine yerleştirilen her karakter _), yeni çizgiden, orta çizgiden, boş bir çizgiden ve alt çizgiden (üst çizgiyle aynı şekilde) oluşan beş satırlı yeni bir listeye katılır .


2

Python 3, 169 168 bayt. (167, Python 2 ile birlikte)

p,s='',str.split
for _ in s('N '.join(s('P '.join(s(input(),'P')),'N'))):
 v=int(_[:-1]);p+=['='*v,('- '*v)[:v]][_[-1]=='P']
l=len(p)
u='_'*l
print(u+'\n'*3+p+'\n\n'+u)

Oldukça ungolfed:

p=''
for i in'N '.join('P '.join(input().split('P')).split('N')).split():

  v=int(i[:-1])         # Get the number from the input section

  if i[-1]=='N':        # Check the letter (last char) from the input section
      p+=('='*v)        # Repeat `=` the number from input (v)
  else:
      p+=('- '*v)[:v]   #Repeat `- ` v times, then take first v chars (half)
l=len(p)                #Get the length of the final line markings
print('_'*l+'\n\n\n'+p+'\n\n'+'_'*l)

print('_'*l                          # Print _ repeated the length of p
           +'\n\n\n'                 # 3 new lines
                    +p+              # print out p (the markings)
                       '\n\n'        # 2 new lines
                             +'_'*l) # Print _ repeated the length of p

for i in
        'N '.join(
                  'P '.join(
                            input().split('P'))
                                               .split('N'))
                                                           .split():
                            # Split the input into items of list at P
                  # Join together with P and ' '
                                                # Split at N...
         # Join with N and ' '
                                                           # Split at space
# Loop through produced list

Burada çevrimiçi deneyin .


Bayt sayısını güncellemeyi unuttun.
mbomb007

@ mbomb007 Sayımı değiştirmedi: / 169 atm'den az alamıyorum
Tim

p+=['='*v,('- '*v)[:v]][_[-1]=='P']Bir önceki satırın sonuna bir noktalı virgül koyarak koymak bir bayttan tasarruf sağlar.
mbomb007

Ayrıca, Python 2 kullanarak yerine 1 bayt kaydeder print.
mbomb007

@ mbomb007 onları ekledi :) Ben bir his python 2 daha kısa olabilir ... Ama emin değilim.
Tim,

2

Python 2, 136 bayt

Şaşırtıcı bir şekilde, ithalat reburada gerçekten faydalı görünmektedir.

import re
s=""
for x,y in re.findall("(\d+)(.)",input()):s+=(("- ","==")[y=="N"]*int(x))[:int(x)]
t="_"*len(s);print t+"\n"*3+s+"\n"*2+t

2

PHP, 187 bayt

preg_match_all('/(\d+)(\w)/',$argv[1],$m,2);
$o='';
foreach($m as $p)
    $o.=str_replace('--','- ',str_repeat($p[2]<'P'?'=':'-',$p[1]));
$a=preg_replace('/./','_',$o);
echo("$a\n\n\n$o\n\n$a\n");

Kod tek bir satırda kalabilir; burada daha okunaklı olmak için birden fazla satırda görüntülenir (biçimlendirme için kullanılan boşluklar ve yeni satırlar sayılmaz).

Sondaki yeni satırı yazdırarak iki bayt kaydedilebilir. Şunlarda gerçek yeni satır karakterleri kullanılarak beş bayt daha kaydedilebilir echo():

echo("$a


$o

$a");

$o( $o='';) Başlaması atlanarak altı ek bayt kaydedilebilir, ancak bu bir uyarı tetikler. Komut satırını kullanarak komut dosyası çalıştırılarak bildirim engellenebilir:

$ php -d error_reporting=0 <script_name> 4N4P9N7P1N1P2N2P

Bunlar onu 174 bayta getiriyor.


2

Ruby, 137 135 bayt

Gelebildiğim en kısa sürede değil, en iyisine yakın. Optimizer’ın cevabından kısmen ödünç alındı.

require'scanf'
N='_  = _'
P='_  - _'
a=[]
scanf('%d%c'){|l,t|a+=[eval(t).chars]*l}
puts (a.shift.zip(*a).map(&:join)*?\n).gsub'--','- '

Ungolfed:

require 'scanf'

N = '_  = _'
P = '_  - _'
columns = [] # array of columns
# scan stdin for a number followed by a single char
scanf('%d%c') do |length, type|
  columns += [eval(type).chars] * length
done

# Convert to an array of rows, and join into a string
rows = columns.shift.zip(*columns).map(&:join)
str = rows * "\n" # join lines

# Replace '--' by '- ' and print
puts str.gsub(/--/, '- ')

Son satırı değiştirerek bunu 2 bayta kadar iyileştirebilmelisiniz (ve python 2 cevabını geçmelisiniz) (a.shift.zip(*a).map(&:join)*?\n).gsub'--','- '.
blutorange

1

C, 155 bayt

main(l,v,k,n,x,s,c)char*s,**v,c;{for(l=6;l--;puts(s))for(s=v[1];*s;s+=k)for(x=sscanf(s,"%d%c%n",&n,&c,&k);n--;)putchar(l%5?l^2?32:c^78?++x&1?45:32:61:95);}

Daha okunabilir:

main(l,v,k,n,x,s,c)
    char*s,**v,c;
{
    for(l=6;l--;puts(s))
        for(s=v[1];*s;s+=k)
            for(x=sscanf(s,"%d%c%n",&n,&c,&k);n--;)
                putchar(l%5?l^2?32:c^78?++x&1?45:32:61:95);
}

Dış döngü 5 ila 0 arasındaki satırları sayar.

Orta döngü kodlanmış dizenin bölümleri üzerinde yinelenir:

4N4P9N7P1N1P2N2P
4P9N7P1N1P2N2P
9N7P1N1P2N2P
7P1N1P2N2P
1N1P2N2P
1P2N2P
2N2P
2P
string is empty - exit

İç döngü bir parçanın kodunu çözer, benzer 7Pve gereken sayıda tekrar eder (örneğin 7).

Her yineleme bir tane basar char. Değeri char, kod tarafından tanımlanır l%5?l^2?32:c^78?++x&1?45:32:61:95:

  • Satır numarası 5 veya 0 ise, baskı 95 ( _)
  • Aksi takdirde, satır numarası 2'ye eşit değilse, bir boşluk yazdırın
  • Aksi takdirde, sembol 'N' ise, 61 ( =)
  • Aksi takdirde, x1 artar (2 ile başlatıldı sscanf)
  • Garipse, 45 ( -) yazdırın, aksi takdirde 32 (boşluk) yazdırın

0

Scala, 163 bayt

(s:String)=>{val r=(("\\d+(P|N)"r) findAllIn(s) map(r=>{val l=r.init.toInt;if(r.last=='N')"="*l else ("- "*l).take(l)})).mkString;val k="_"*r.length;s"$k\n\n\n$r\n\n$k"}

İlk deneme, biraz daha golf oynayabilir.


0

Ruby, 94 bayt

Bu gsub'--','- 'fikri 14mRh4X0r'nin cevabından ödünç alır . Bence bu daha kısa olmasına rağmen cevabın daha ilginç olduğunu düşünüyorum.

f=->x{n=?_*x.gsub!(/(\d+)(.)/){($2==?P??-:?=)*$1.to_i}.size
"#{n}


#{x.gsub'--','- '}

#{n}"}

Test yapmak:

f=->x{n=?_*x.gsub!(/(\d+)(.)/){($2==?P??-:?=)*$1.to_i}.size
"#{n}


#{x.gsub'--','- '}

#{n}"}

puts f['4N4P9N7P1N1P2N2P']

üretir:

______________________________


====- - =========- - - -=-==- 

______________________________

0

benim şunlardır izin matlab versiyonunu

MATLAB (267 b)

function d=p(V,a),j=numel(V)-1;if (a==0),d=0;return; end,d=(V(a)-48+10*p(V,a-1))*(V(a)<64);fprintf('%c%.*s%c%.*s',(a>=j)*10,(a==j|a==1)*eval(strcat(regexprep(V,'[NP]','+'),48)),ones(99)*'_',(a<3)*10,(V(a+1)>64)*d,repmat((V(a+1)==78)*'=='+(V(a+1)==80)*'- ',[1 99]));end

giriş

Boşluk biçiminde ascii biçimli bir dize (matlabda '\ 0' zincirinin sonu olmadığından

örnek V = '12N13P'


çıktı

yolun desen temsili

_________________________


============- - - - - - -

_________________________

fonksiyon

İşlev tail-1'den çağrılmalıdır (boş karakter kaldırılmıştır).

örnek : p (V, sayı (V) -1)

Simülasyon

burada çevrimiçi deneyin


0

R, 132 bayt

Bundan çok mutlu değil, ama yapmak biraz eğlenceliydi :) Birden fazla gsubkişiden kurtulmaya çalıştım , ama çabalarım boşunaydı. Bunu yapmanın daha iyi bir yolu olduğunu düşünüyorum.

cat(rbind(nchar(a<-scan(,'',t=gsub('PN','P N',gsub('NP','N P',chartr('- =','PPN',scan(,'',sep='|')[4]))))),substring(a,1,1)),sep='')
  • scandizeleri STDIN'den alır ve dördüncü olanı yakalar. NotBoş satırların, taramaya girdi almak için aralarında boşluk (veya başka bir şey) gerektiğini .

    "==== - - ========= - - - - = - == -"

  • O değiştirir =ile s Ns, -ve ile Ps.

    "NNNNPPPPNNNNNNNNNPPPPPPPNPNNPP"

  • Sonra her biri NPile arasında bir boşluk ekler.PN

    "NNNN PPPP NNNNNNNNN PPPPPPP NP NN PP"

  • Tarama dizeyi boşluklara böler

    "NNNN" "PPPP" "NNNNNNNNN" "PPPPPPP" "N" "P" "NN" "PP"

  • Dize uzunluğu daha sonra rbindher dizenin ilk karakteriyle sınırlanır ( ).

    4 4 9 7 1 1 2 2
    "N" "P" "N" "P" "N" "P" "N" "P"

  • Dizi daha sonra kullanılarak çıkar cat.

Test sürüşü

cat(rbind(nchar(a<-scan(,'',t=gsub('PN','P N',gsub('NP','N P',chartr('- =','PPN',scan(,'',sep='|')[4]))))),substring(a,1,1)),sep='')
1: ____________
2:  
3:  
4: ============
5:  
6: ____________
7: 
Read 6 items
Read 1 item
12N
> 
> cat(rbind(nchar(a<-scan(,'',t=gsub('PN','P N',gsub('NP','N P',chartr('- =','PPN',scan(,'',sep='|')[4]))))),substring(a,1,1)),sep='')
1: ____________
2:  
3:  
4: - - - - - - 
5:  
6: ____________
7: 
Read 6 items
Read 1 item
12P
> cat(rbind(nchar(a<-scan(,'',t=gsub('PN','P N',gsub('NP','N P',chartr('- =','PPN',scan(,'',sep='|')[4]))))),substring(a,1,1)),sep='')
1: ______________________________
2:  
3:  
4: ====- - =========- - - -=-==- 
5:  
6: ______________________________
7: 
Read 6 items
Read 8 items
4N4P9N7P1N1P2N2P
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.