닌자 원숭이와 곰, 오 마이!


37

이 도전은 닌자 베어 몽키 (NinjaBearMonkey) 가 내 블록 빌딩 봇 무리 (Block Building Bot Flocks) 를 수상한 상입니다 ! 흑기사 제출에 도전하십시오 . 축하합니다 NinjaBearMonkey!

여기서의 과제는 매우 간단하지만 다양한 방법이 있습니다. 이야기는 Isometric Illusions 세계 에는 6 가지 유형의 생물이 있다는 것입니다.

  1. 닌자, 약자 N
  2. 약식 곰 B
  3. 원숭이, 약자 M
  4. 닌자 곰, 약어 NB
  5. BearMonkeys, 약자 BM
  6. NinjaBearMonkeys, 약어 NBM

( NinjaBearMonkey은 물론, 마지막으로, 가장 강력한 형태입니다.)

당신의 임무는 나란히 줄 지어있을 때, 즉 그들의 약자 줄이 연결되어있을 때이 생물체들에 대한 인구 조사 를하는 것입니다. 주의해야 할 점은 일부 생물의 일부를 유사하게 보이는 별도의 생물로 과대 계산하지 않도록해야한다는 것입니다. 그 생물들은 다음과 같이 줄을 서게됩니다 :

  • 인스턴스 NBM는 1 개의 NinjaBearMonkey와 0 개의 다른 생물입니다.
  • NB뒤에 오지 않는 인스턴스 M는 1 개의 NinjaBear와 0 개의 다른 생물입니다.
  • BM선행하지 않는 인스턴스 N는 1 BearMonkey 및 0 다른 생물입니다.
  • 그렇지 않으면, 인스턴스 N, B그리고 M하나의 닌자, 곰, 원숭이가 각각 있습니다.

행은 왼쪽에서 오른쪽으로 읽습니다.

예를 들어, 생물 라인 NBMMBNBNBM에는 닌자 0 개, 곰 1 마리, 원숭이 1 마리, 닌자 베어 1 마리, 곰 몽키 0 마리, 닌자 비어 몽키 2 개가 있습니다.

도전

문자의 문자열에 걸리는 프로그램이나 기능 쓰기 N, BM, 및 인쇄 또는 생물의 6 종류의 각각의 많은 사람들이 거기에 존재하는 방법을 반환합니다.

출력 양식이 있어야합니다

#N #B #M #NB #BM #NBM

각각의 생물 수는 각 #표지판을 대체합니다 . 6 개가 모두 0 인 경우에도 공백으로 구분하여 표시해야합니다. 그러나 순서는 상관 없습니다 (예 : #NBM먼저 올 수 있음).

또한:

  • 입력 문자열은 문자 만 포함 N, BM.
  • 빈 문자열이 입력되면 모든 카운트는 0입니다.
  • 출력은 선택적으로 단일 선행 및 / 또는 후행 공간 및 / 또는 단일 후행 줄 바꿈을 포함 할 수 있습니다.

바이트 단위의 최단 제출이 이깁니다.

입력 : NB
출력 :0N 0B 0M 1NB 0BM 0NBM

입력 : NBM
출력 :0N 0B 0M 0NB 0BM 1NBM

입력 : NBMMBNBNBM(위의 예)
출력 :0N 1B 1M 1NB 0BM 2NBM

입력 : MBNNBBMNBM
출력 :1N 1B 1M 1NB 1BM 1NBM

입력 : NNNMNBMMBMMBMMMNBMNNMNNNBNNNBNBBNBNMMNBBNBMMBBMBMBBBNNMBMBMMNNNNNMMBMMBM
출력 :17N 6B 14M 5NB 8BM 3NBM


53
이 과제를 승인합니다.
NinjaBearMonkey 2016 년

확인하기 위해 : 당신이 가진 모든 것이 2 개의 NinjaBearMonkeys라면, 당신은 라인을 형성 할 수 없습니까? 그들은 서로 옆에 설 수 없기 때문에?
Alan Campbell

3
@AlanCampbell No. NBMNBM는 완벽하게 유효한 입력입니다. 왼쪽에서 오른쪽으로 읽으면 분명히 2 개의 NinjaBearMonkey가 있습니다.
Calvin 's Hobbies

답변:


20

Pyth, 22 바이트

 f|pd+/zTT=:zTd_.:"NBM

@Jakube 덕분에 1 바이트를 절약하는 해킹 방법.


Pyth, 23 바이트

FN_.:"NBM")pd+/zNN=:zNd

데모.

후행 공백없이 후행 줄 바꿈없이 역순으로 인쇄합니다.

.:"NBM")모든 하위 문자열이며, _올바른 순서 로 배치 /zN하고, 발생 횟수를 세고, =:zNd해당 문자열의 각 발생을 공백으로 대체합니다.

FN_.:"NBM")pd+/zNN=:zNd
FN                         for N in                            :
  _                                 reversed(                 )
   .:     )                                  substrings(     )
     "NBM"                                              "NBM"
           pd              print, with a space at the end,
              /zN          z.count(N)
             +   N                    + N
                  =:zNd    replace N by ' ' in z.

23

자바 스크립트 ES6, 86 바이트

f=s=>'NBM BM NB M B N'.replace(/\S+/g,e=>(i=0,s=s.replace(RegExp(e,'g'),_=>++i))&&i+e)

(방금 이것에 대답해야했습니다.) NBM더 긴 문자열 부터 시작하여 더 높은 우선 순위를 갖는의 각 하위 문자열을 통과합니다 . 특정 문자열의 각 항목을 검색하여 제거합니다 (이 경우 문자열을 현재 개수로 바꾸어 다시 일치하지 않음). 마지막으로 각 하위 문자열을 count + 문자열로 바꿉니다.

이 스택 스 니펫은 모든 브라우저에서 쉽게 테스트 할 수 있도록 위의 코드와 동일한 ES5로 작성되었습니다. 약간 ungolfed 코드이기도합니다. 키를 누를 때마다 UI가 업데이트됩니다.

f=function(s){
  return'NBM BM NB M B N'.replace(/\S+/g,function(e){
    i=0
    s=s.replace(RegExp(e,'g'),function(){
      return++i
    })
    return i+e
  })
}

run=function(){document.getElementById('output').innerHTML=f(document.getElementById('input').value)};document.getElementById('input').onkeyup=run;run()
<input type="text" id="input" value="NBMMBNBNBM" /><br /><samp id="output"></samp>


정규식 부분을로 바꿀 수 있습니까? 'NBM<newline>BM<newline>...<newline>N'.replace(/./g, ...)'여기서 <newline>s는 리터럴 개행이고 's는 백틱이며 ES6 템플릿 문자열을 형성합니까? 정규식에 2 바이트를 저장합니다 (줄 바꾸기 .와 일치하지 않음).
wchargin 2016 년

@WChargin 불행히도, 출력은 공백으로 구분되어야하므로 아니요.
NinjaBearMonkey

17

파이썬 2, 78

n=input()
for x in"NBM BM NB M B N".split():n=`n`.split(x);print`len(n)-1`+x,

Vioz-의 답변 변형 . 파이썬 2 문자열 표현으로 재미있게!

부분 문자열을 분할하고 부분을 세고 1을 빼서 부분 문자열의 발생을 간접적으로 계산합니다. 부분 문자열을 필러 기호로 바꾸는 대신 문자열을 split생성 된 목록으로 바꿉니다 . 그런 다음 문자열 표현을 할 때 부분은 공백과 쉼표로 구분됩니다.


5
미쳤다! 훌륭하게 미쳤지 만 여전히 미쳤습니다.
Sp3000

잘 했어! 그것을 생각하지 않았다 :)
Kade

14

루비, 166 80 72 68 자

f=->s{%w(NBM BM NB M B N).map{|t|c=0;s.gsub!(t){c+=1};c.to_s+t}*' '}

설명:

  • 계산은 반대로 수행됩니다. 긴 닌자와 곰, 원숭이가 짧은 닌자보다 우선하기 때문입니다.

  • 들면 NBM, BMNB, 시퀀스가 gsub!존재 방법이 많은 시퀀스 카운트 블록과 원래의 문자열의 출력 D '(예, 함수의 인수를 변경).

    • 그렇지 않은 경우가 있기 때문에, 그들은 아무것도 대체 할 수없는 BNBMM등의 계산 될 수 NBMBM대신 B, NBMM합니다 (이 때 때문에 NBM제거 할 것, 그것은을 둘 것 BM함께 그것을 구별 할 수있는 방법이 없을 것이다). 원래 단일 문자열 ( .gsub!('NBM'){c+=1;?|})을 반환했지만 결과를 반환 할 수 있음을 깨달았습니다 +=(숫자이므로 어떤 것도 될 수 없음 N B M).
  • 를 들어 M, B그리고 N, 난 그냥 수 count문자열에이 얼마나 그들 중 많은 (필요 통해 제거 없습니다 gsub!). 이제 루프입니다 (왜 처음에 그것을 생각하지 않았는지 모르겠습니다). 이것들은 같은 방식으로 이루어집니다.


타조의 비슷한 솔루션 , 54 51 자 :

:s;`NBM BM NB M B N`" /{:t0:n;s\{;n):n}X:s;nt+}%" *

불행히도 현재 Ostrich 버전에 버그가 있기 때문에 올바른 해결책은 아닙니다 (현재 수정되었지만이 문제가 게시 된 후).


배열 표기법을 사용 %w(NBM BM NB M B N)하고 분할을 제거 하여 3 개의 문자를 저장할 수 있습니다 .
DickieBoy

@DickieBoy 실제로 4 자입니다. 감사!
Doorknob

아 맞아요!
DickieBoy 2016 년

14

자바 166 162

void f(String a){String[]q="NBM-NB-BM-N-B-M".split("-");for(int i=0,c;i<6;System.out.print(c+q[i++]+" "))for(c=0;a.contains(q[i]);c++)a=a.replaceFirst(q[i],".");}

그리고 몇 줄 바꿈 :

void f(String a){
    String[]q="NBM-NB-BM-N-B-M".split("-");
    for(int i=0,c;i<6;System.out.print(c+q[i++]+" "))
        for(c=0;a.contains(q[i]);c++)
            a=a.replaceFirst(q[i],".");
}

꽤 간단하게 작동합니다. 입력에 토큰이 포함되어있는 한, 토큰을 반복하여 점으로 대체하고 계산하십시오. 큰 것을 먼저 계산하여 작은 것을 엉망으로 만들지 않습니다.

원래 한 번에 모두 바꾸고 길이의 차이를 세려고 시도했지만 그런 식으로 몇 문자가 더 필요했습니다. (


2
Java 개발자로서 나는 이것을 더 짧게 만들고 Java가 변화를 위해 승리하는 것을보고 싶다. 잠시 동안 그것을 쳐다 본 후에 나는 그것을 더 짧게 만드는 방법을 아직 찾지 못했습니다.
DeadChex

1
글쎄, 그것은 확실히 전체적으로 이길 수 없습니다 . 현재 리더는 22 바이트이며 Java에서 그 크기로 의미있는 것을 할 수있는 방법이 없습니다. 내 println말만으로는 그것보다 큽니다. 그래도 만족합니다 : D
Geobits

1
조금 늦었지만 방법을 찾았습니다 ... 다음 String q[]=으로 변경String[]q=
DeadChex

1
좋은! 내가 그것을 놓쳤다는 것을 믿을 수 없어, 그것은 볼 것의 표준 목록에 있습니다 :)
Geobits

나는 단지 JavaDev로 코드 골프에려고 후에 발견, 나는 확실히 당신이 할 수있는 것들 중 일부에 놀랄거야
DeadChex

11

CJam, 36 32 31 바이트

l[ZYX]"NBM"few:+{A/_,(A+S@`}fA;

1 바이트로 골프를 치는 @Optimizer에게 감사드립니다.

CJam 통역사 에서 온라인으로 사용해보십시오 .

작동 원리

l                                e# Read a line L from STDIN.
 [ZYX]"NBM"                      e# Push [3 2 1] and "NBM".
           few                   e# Chop "NBM" into slices of length 3 to 1.
              :+                 e# Concatenate the resulting arrays of slices.
                {          }fA   e# For each slice A:
                 A/              e#   Split L at occurrences of A.
                   _,(           e#   Push the numbers of resulting chunks minus 1.
                      A+         e#   Append A.
                        S        e#   Push a space.
                         @`      e#   Push a string representation of the split L.
                              ;  e# Discard L.

N*-> `충분해야합니다.
Optimizer

@ 최적화 : 잘 작동합니다. 감사.
Dennis

7

R, 153 (134) 118

이것은 정말로 더 길어졌지만 희망적으로 몇 가지를 면도 할 수 있기를 바랍니다. 입력은 STDIN이며 STDOUT으로 출력됩니다.

압정 변경을 편집합니다 . 분할 문자열과 계수 부품을 제거했습니다. 이제 부품보다 짧은 문자열로 부품을 교체합니다. 문자열 길이의 차이는 출력을 위해 수집됩니다.

N=nchar;i=scan(,'');for(s in scan(,'',t='NBM BM NB M B N'))cat(paste0(N(i)-N(i<-gsub(s,strtrim('  ',N(s)-1),i)),s),'')

설명

N=nchar;
i=scan(,'');                     # Get input from STDIN
for(s in scan(,'',t='NBM BM NB M B N'))  # Loop through patterns
  cat(                           # output
    paste0(                      # Paste together
      N(i) -                     # length of i minus
      N(i<-gsub(                 # length of i with substitution of
        s,                       # s
        strtrim('  ',N(s)-1)     # with a space string 1 shorter than s
        ,i)                      # in i
      ),
      s)                         # split string
  ,'')

시운전

> N=nchar;i=scan(,'');for(s in scan(,'',t='NBM BM NB M B N'))cat(paste0(N(i)-N(i<-gsub(s,strtrim('  ',N(s)-1),i)),s),'')
1: NNNMNBMMBMMBMMMNBMNNMNNNBNNNBNBBNBNMMNBBNBMMBBMBMBBBNNMBMBMMNNNNNMMBMMBM
2: 
Read 1 item
Read 6 items
3NBM 8BM 5NB 14M 6B 17N 
> N=nchar;i=scan(,'');for(s in scan(,'',t='NBM BM NB M B N'))cat(paste0(N(i)-N(i<-gsub(s,strtrim('  ',N(s)-1),i)),s),'')
1: NBMMBNBNBM
2: 
Read 1 item
Read 6 items
2NBM 0BM 1NB 1M 1B 0N 
> 

7

Pyth, 19 바이트

jd+Ltl=zc`zd_.:"NBM

이것은 @isaacg의 Pyth 솔루션과 @xnor의 놀라운 Python 트릭이 혼합되어 있습니다.

온라인으로 사용해보십시오 : 데모 또는 테스트 장치

설명

jd+Ltl=zc`zd_.:"NBM   implicit: z = input string
             .:"NBM   generate all substrings of "NBM"
            _         invert the order
  +L                  add left to each d in ^ the following:
         `z             convert z to a string
        c  d            split at d
      =z                assign the resulting list to z
    tl                  length - 1
jd                    join by spaces and implicit print

6

줄리아, 106 97 바이트

b->for s=split("NBM BM NB M B N") print(length(matchall(Regex(s),b)),s," ");b=replace(b,s,".")end

이것은 문자열을 입력으로 사용하여 결과를 단일 후행 공백과 후행 줄 바꿈없이 STDOUT에 인쇄하는 명명되지 않은 함수를 작성합니다. 호출하려면 이름을 지정하십시오 (예 :) f=b->....

언 골프 + 설명 :

function f(b)
    # Loop over the creatures, biggest first
    for s = split("NBM BM NB M B N")

        # Get the number of creatures as the count of regex matches
        n = length(matchall(Regex(s), b))

        # Print the number, creature, and a space
        print(n, s, " ")

        # Remove the creature from captivity, replacing with .
        b = replace(b, s, ".")
    end
end

예 :

julia> f("NBMMBNBNBM")
2NBM 0BM 1NB 1M 1B 0N 

julia> f("NNNMNBMMBMMBMMMNBMNNMNNNBNNNBNBBNBNMMNBBNBMMBBMBMBBBNNMBMBMMNNNNNMMBMMBM")
3NBM 8BM 5NB 14M 6B 17N 

4

파이썬 2, 93 88 89 84 바이트

직접적인 접근

def f(n):
 for x in"NBM BM NB M B N".split():print`n.count(x)`+x,;n=n.replace(x,"+")

이렇게 전화하십시오 :

f("NBMMBNBNBM")

출력은 다음과 같습니다.

2NBM 0BM 1NB 1M 1B 0N

뒤에 공백을 제거 할 수 있습니다 in.
isaacg 2016 년

파이썬 2에서는`x`를 사용하여 문자열 표현으로 변환 할 수 있습니다.
xnor

4

SAS, 144 142 139 129

data;i="&sysparm";do z='NBM','NB','BM','N','B','M';a=count(i,z,'t');i=prxchange(cats('s/',z,'/x/'),-1,i);put a+(-1)z@;end;

사용법 (sysparm에 7 바이트 추가) :

$ sas -stdio -sysparm NNNMNBMMBMMBMMMNBMNNMNNNBNNNBNBBNBNMMNBBNBMMBBMBMBBBNNMBMBMMNNNNNMMBMMBM << _S
data;i="&sysparm";do z='NBM','NB','BM','N','B','M';a=count(i,z,'t');i=prxchange(cats('s/',z,'/x/'),-1,i);put a+(-1)z@;end;
_S

또는

%macro f(i);i="&i";do z='NBM','NB','BM','N','B','M';a=count(i,z,'t');i=prxchange(cats('s/',z,'/x/'),-1‌​,i);put a+(-1)z@;end;%mend;

용법:

data;%f(NNNMNBMMBMMBMMMNBMNNMNNNBNNNBNBBNBNMMNBBNBMMBBMBMBBBNNMBMBMMNNNNNMMBMMBM)

결과:

3NBM 5NB 8BM 17N 6B 14M

cats('s/',z,'/x/')대신에 몇 바이트를 저장할 수 있습니다 's/'||strip(z)||'/x/'.
Alex A.

1
니스, 그것은 139에 꽤 여행이었다 :)
프라이드 에그

1
126 바이트 :macro a i="&sysparm";do z='NBM','NB','BM','N','B','M';a=count(i,z,'t');i=prxchange(cats('s/',z,'/x/'),-1,i);put a+(-1)z@;end;%
Alex A.

1
122 : data;i="&sysparm";do z='NBM','NB','BM','N','B','M';a=count(i,z,'t');i=prxchange(cats('s/',z,'/x/'),-1,i);put a+(-1)z@;end;. 에서 이미 읽고 있기 때문에 sysparm데이터 단계로 실행할 수도 있습니다. 배치로 실행하는 경우 필요하지 않습니다 run;.
Alex A.

1
그러나 명령 줄 인수에서 읽지 않는 현대적인 매크로를 사용하면 129를 얻을 수 있습니다.%macro a(i);i="&i";do z='NBM','NB','BM','N','B','M';a=count(i,z,'t');i=prxchange(cats('s/',z,'/x/'),-1,i);put a+(-1)z@;end;%mend;
Alex A.

3

PHP4.1, 92 바이트

가장 짧은 것은 아니지만 PHP에서 무엇을 기대하십니까?

그것을 사용하려면 쿠키, POST, GET, 세션에서 키를 설정하십시오.

<?foreach(split(o,NBMoNBoBMoMoBoN)as$a){echo count($T=split($a,$S))-1,"$a ";$S=join('',$T);}

접근 방식은 기본입니다.

  • 줄을 생물의 이름으로 나눕니다.
  • 얼마나 많은 요소가 있는지 계산
  • 1 빼기 (빈 문자열은 요소가 1 개인 배열을 제공함)
  • 카운트와 생물 이름을 출력
  • 빈 줄을 사용하여 모두 연결하십시오 (줄을 줄이고 마지막 생물을 제거합니다)

쉬워요?


2

자바 스크립트, 108 116 바이트

간단한 접근 방식, 멋진 것은 아닙니다.

o="";r=/NBM|NB|BM|[NMB]/g;g={};for(k in d=(r+prompt()).match(r))g[d[k]]=~-g[d[k]];for(k in g)o+=~g[k]+k+" ";alert(o);

1
작동하지 않습니다 : All 6 counts must be shown, separated by spaces, even when they are 0.. 테스트 사례 :N
edc65

트윗 담아 가기 나는 그 부분을 놓쳤다. 지적 해 주셔서 감사합니다. 8chars의 비용을 고정
C5H8NNaO4

2

펄, 46

#!perl -p
$_="NBM BM NB M B N"=~s/\w+/~~s!$&!x!g.$&/ger

이것이 어떻게 작동하는지에 대한 설명?
가인

1

SpecBAS-164

1 INPUT s$
2 FOR EACH a$ IN ["NBM","BM","NB","M","B","N"]
3 LET n=0
4 IF POS(a$,s$)>0 THEN INC n: LET s$=REPLACE$(s$,a$,"-"): GO TO 4: END IF
5 PRINT n;a$;" ";
6 NEXT a$

다른 많은 사람들과 동일한 접근 방식을 사용합니다. 4 행은 문자열을 계속 반복하여 (가장 큰 것부터) 찾은 경우 대체합니다.

SpecBAS는 내가 아직도 알아 내고있는 오리지널 ZX / Sinclair BASIC (목록을 통해 반복, 문자 찾기)을 잘 다루었습니다.


1

C, 205 (186) 184 바이트

상태 머신을 기반으로 한 약간 다른 접근 방식. t상태는 어디에 있습니까 ?

a[7],t,i;c(char*s){do{i=0;t=*s==78?i=t,1:*s-66?*s-77?t:t-4?t-2?i=t,3:5:6:t-1?i=t,2:4;i=*s?i:t;a[i]++;}while(*s++);printf("%dN %dB %dM %dNB %dBM %dNBM",a[1],a[2],a[3],a[4],a[5],a[6]);}

넓히는

int a[7],t,i;

void c(char *s)
{
    do {
        i = 0;
        if (*s == 'N') {
            i=t; t=1;
        }
        if (*s == 'B') {
            if (t==1) {
                t=4;
            } else {
                i=t;
                t=2;
            }
        }
        if (*s == 'M') {
            if (t==4) {
                t=6;
            } else if (t==2) {
                t=5;
            } else {
                i=t;
                t=3;
            }
        }
        if (!*s)
            i = t;
        a[i]++;
    } while (*s++);
    printf("%dN %dB %dM %dNB %dBM %dNBM",a[1],a[2],a[3],a[4],a[5],a[6]);
}

테스트 기능

#include <stdio.h>
#include <stdlib.h>

/*
 * 0 : nothing
 * 1 : N
 * 2 : B
 * 3 : M
 * 4 : NB
 * 5 : BM
 * 6 : NBM
 */
#include "nbm-func.c"

int main(int argc, char **argv)
{
    c(argv[1]);
}

일부 바이트 for(;;*s++){...}do{...}while(*s++);저장 하는 대신 사용 하지 않습니까? 또한에 개행 문자가 필요하지 않습니다 printf.
Spikatrix

나는 당신이 의미하는 것 같아요 for(;*s;s++). 그러나 마지막 널 문자로 반복해야했습니다. 을 (를) 저장하는 \n데 도움이되며 필요하지 않습니다.
일부 사용자

1

C, 146

f(char*s)
{
  char*p,*q="NBM\0NB\0BM\0N\0B\0M",i=0,a=2;
  for(;i<6;q+=a+2,a=i++<2)
  {
    int n=0;
    for(;p=strstr(s,q);++n)*p=p[a>1]=p[a]=1;
    printf("%d%s ",n,q);
  }
}

// Main function, just for testing
main(c,a)char**a;{
  f(a[1]);
}  

1

Haskell-177 바이트 (가져 오기 없음)

n s=c$map(\x->(show$length$filter(==x)(words$c$zipWith(:)s([f(a:[b])|(a,b)<-zip s(tail s)]++[" "])))++x++" ")l
f"NB"=""
f"BM"=""
f p=" "
l=["N","B","M","NB","BM","NBM"]
c=concat

(인터넷 괴로움은 여기에서 유감입니다.)

Haskell 플랫폼에는 가져 오기없이 문자열 검색이 없으며 검색 된 문자열이 모두 하나의 하위 문자열 (반복없이)이라는 사실을 과시하고 악용하여 그룹화 문자를 허용하는 쌍을 식별하여 수행 할 수 있습니다 서로를 따라가는 f것이 여기에 있습니다.

나는 l평등을 확인하고 필요에 따라 정확하게 표시하기 위해 결국 전체 목록 이 필요하지만, 가능한 words순서대로 발생 횟수를보고하는 것이 어려울 수 는 없었습니다.


0

배쉬-101

I=$1
for p in NBM BM NB M B N;{ c=;while [[ $I =~ $p ]];do I=${I/$p/ };c+=1;done;echo -n ${#c}$p\ ;}

문자열을 첫 번째 인수로 전달하십시오.

bash nmb.sh MBNNBBMNBM 

조금 설명했다 :

# We have to save the input into a variable since we modify it.
I=$1

# For each pattern (p) in order of precedence
for p in NBM BM NB M B N;do
    # Reset c to an empty string
    c=

    # Regexp search for pattern in string
    while [[ $I =~ $p ]];do
        # Replace first occurance of pattern with a space
        I=${I/$p/ }
        # Append to string c. the 1 is not special it could be any other
        # single character
        c+=1
    done

    # -n Suppress's newlines while echoing
    # ${#c} is the length on the string c
    # Use a backslash escape to put a space in the string.
    # Not using quotes in the golfed version saves a byte.
    echo -n "${#c}$p\ "
done

0

rs , 275 바이트

(NBM)|(NB)|(BM)|(N)|(B)|(M)/a\1bc\2de\3fg\4hi\5jk\6l
[A-Z]+/_
#
+(#.*?)a_b/A\1
+(#.*?)c_d/B\1
+(#.*?)e_f/C\1
+(#.*?)g_h/D\1
+(#.*?)i_j/E\1
+(#.*?)k_l/F\1
#.*/
#
#(A*)/(^^\1)NBM #
#(B*)/(^^\1)NB #
#(C*)/(^^\1)BM #
#(D*)/(^^\1)N #
#(E*)/(^^\1)B #
#(F*)/(^^\1)M #
\(\^\^\)/0
 #/

라이브 데모 및 테스트.

작업은 간단하지만 조금 이상합니다.

(NBM)|(NB)|(BM)|(N)|(B)|(M)/a\1bc\2de\3fg\4hi\5jk\6l

이것은 창조적으로 그룹을 사용하여 다음과 같이 입력을 설정합니다.

NBMBM

으로

aNBMbcdeBMfghijkl

다음 줄 :

[A-Z]+/_

대문자 순서를 밑줄로 바꿉니다.

#

이것은 단순히 줄의 시작 부분에 파운드 기호를 삽입합니다.

+(#.*?)a_b/A\1
+(#.*?)c_d/B\1
+(#.*?)e_f/C\1
+(#.*?)g_h/D\1
+(#.*?)i_j/E\1
+(#.*?)k_l/F\1
#.*/

이것은 멋진 시작 부분입니다. 기본적으로 소문자와 밑줄 순서를 사용하여 대문자로 변환하고 그룹화 한 다음 삽입 된 파운드 앞에 배치합니다. 파운드의 목적은 이미 처리 된 시퀀스를 관리하는 것입니다.

#

파운드는 줄의 시작 부분에 다시 삽입됩니다.

#(A*)/(^^\1)NBM #
#(B*)/(^^\1)NB #
#(C*)/(^^\1)BM #
#(D*)/(^^\1)N #
#(E*)/(^^\1)B #
#(F*)/(^^\1)M #
\(\^\^\)/0
 #/

대문자는 관련 카운트와 동일한 텍스트로 대체됩니다. rs에 버그가 있기 때문에 (나는 그것을 고치고 실격을 당하지 않으려 고 함) 빈 시퀀스가로 변환되어 (^^)마지막에서 두 번째 줄의 0으로 바뀝니다. 마지막 줄은 단순히 파운드를 제거합니다.


0

KDB (Q), 76 바이트

{" "sv string[-1+count@'enlist[x]{y vs" "sv x}\l],'l:" "vs"NBM NB BM N B M"}

설명

                                                   l:" "vs"NBM NB BM N B M"     / substrings
                        enlist[x]{y vs" "sv x}\l                                / replace previous substring with space and cut
              -1+count@'                                                        / counter occurrence
       string[                                  ],'                             / string the count and join to substrings
{" "sv                                                                     }    / concatenate with space, put in lambda

테스트

q){" "sv string[-1+count@'enlist[x]{y vs" "sv x}\l],'l:" "vs"NBM NB BM N B M"}"NNNMNBMMBMMBMMMNBMNNMNNNBNNNBNBBNBNMMNBBNBMMBBMBMBBBNNMBMBMMNNNNNMMBMMBM"
"3NBM 5NB 8BM 17N 6B 14M"
q){" "sv string[-1+count@'enlist[x]{y vs" "sv x}\l],'l:" "vs"NBM NB BM N B M"}""
"0NBM 0NB 0BM 0N 0B 0M"

0

하스켈 : 244 바이트

import Data.List
s="NBM"
[]#_=[[]]
a#[]=[]:a#s
l@(a:r)#(b:m)
 |a==b=let(x:y)=r#m in((a:x):y)
 |True=[]:l#m
c?t=length$filter(==t)c
p=["N","B","M","NB","BM","NBM"]
main=getLine>>= \l->putStrLn.intercalate " "$map(\t->show((l#[])?t)++t)p

몇 가지 제안 : 사용 p하고 s한 번만 사용 하므로 이름을 지정할 필요가 없습니다 (-> a#[]=[]:a#"NBM"와 동일 p). BTW : words"N B M NB BM NBM"문자열 목록 대신 추가 바이트를 저장합니다. 의 import경우에만 intercalate, 다시 구현하는 데 걸리는 시간이 더 짧 ...putStrLn.tail.((' ':)=<<)$map...습니다 import. 모든 경비원 |#한 줄로 정의 하여 다음 1<2대신 사용하십시오 True. ...#(b:m)|a==b=...l#m|1<2=[]......
nimi

... ?목록 이해를 통해 더 짧게 정의 할 수 있습니다 c?t=sum[1|x<-c,x==t]. 다시 ?한 번만 사용하므로 본문을 직접 사용하십시오 ...show(sum[1|x<-l#[],x==t]).
nimi
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.