숫자 속기를 사용하여 표현식 평가


10

사용자 친화적 인 계산기를 만들고자하는 회사에서 일하고 있으므로 사용자가 "숫자 속기", 즉와 같은 숫자 값을 나타내는 문자를 사용할 수있는 기능을 추가해야 k합니다 1000. 회사는 상기 계산기의 저장 비용을 절감하기를 원하므로 저장 비용을 줄이기 위해 코드를 최대한 최소화해야합니다.


당신의 작업

STDIN에서 입력으로 표현식을 읽거나 매개 변수로 가져 와서 평가를 리턴하거나 STDOUT에 인쇄하는 함수를 작성해야합니다.

일부 설명

몇 가지 정의를하겠습니다. 먼저, 입력 값이 있는데,이를 표현식이라고합니다. 이것은 다음과 같습니다.

x + y / z

이 표현식 내에서 우리는 세 개의 숫자가 있습니다 x, y그리고 z사업자 (로 구분 +하고 /). 이 숫자는 반드시 양의 정수 (또는 정수) 일 필요는 없습니다. 문제를 복잡하게 만드는 것은 숫자 안에 포함 된 속기를 평가해야 할 때입니다. 예를 들어

2k15

평가 목적으로이를 2, 1000( k) 및 15. 그런 다음 규칙에 따라

2*1000 + 15 = 2015

이 방법을 사용하면 다음 규칙을 이해하기가 더 쉬워집니다.

규칙

NB 달리 명시되지 않는 한, "숫자"또는 그 동의어를 속기를 포함하도록 해석 할 수 있습니다.

  1. 다음은 함수가 처리 할 수있는 숫자 속기 k, m, b, t, and e입니다. k, m, b, and t값에 1000, 1000000, 1000000000, and 1000000000000각각 해당합니다 (1,000, 백만, 10 억 및 1 조). e속기는 항상 다른 번호 다음에 할 것 n, 그리고 나타냅니다 10^n. 당신은 숫자 속기 (short 단축)가 n전에 나타나고 있어야한다 e. 예를 들어로 kek평가됩니다 1000*10^1000.

  2. 간단히하기 위해 숫자가 줄어든 경우 e한 번만 사용됩니다.

  3. 속기 전의 모든 숫자 ( 속기 포함 )에 곱하기가 있습니다. 예를 들어 120kk로 평가됩니다 120 * 1000 * 1000. 그 앞에 숫자가 없으면 숫자가 1이라고 가정해야합니다 (수학에서 변수를 x내재적으로 처리하는 방법 과 같이 1x). 예를 들어로 e10평가합니다 10^10. 또 다른 예 :로 2m2k평가됩니다 2*1000000*2*1000(아무것도 추가되지 않음).

  4. 속기가 포함 된 숫자에서 마지막 속기 다음에 오는 숫자 (속기는 해당되지 않음) 가 추가됩니다. 예를 들어 2k12로 평가됩니다 2*1000 + 12. 단수형 e을 사용하는 경우 는 예외 이며,이 경우 다음 수 ( 약수 포함 ) e가 취급 n되고 평가됩니다 10^n(첫 번째 규칙 참조).

  5. 함수는 +, -, *, and /각각 더하기, 빼기, 곱하기 및 나누기 연산자를 처리 할 수 ​​있어야합니다 . 원하는 경우 더 처리 할 수 ​​있습니다.

  6. 작업 순서에 따라 작업이 평가됩니다 .

  7. 속기의 숫자는 정수만이 아닙니다. 3.5b1.2유효하며 다음과 같이 평가됩니다3.5*1000000000 + 1.2 = 3500000001.2

  8. 이런 종류의 것들이 있다면 내장 기능은 허용되지 않습니다. 내가 추가 할 예외는 언어가 자동으로 많은 수를 과학적 표기법으로 변환하는 경우입니다.이 경우 출력에 허용됩니다.

  9. 바이트 단위의 가장 짧은 코드가 승리하고 표준 허점이 적용됩니다.

입력

입력은 각 숫자와 연산자가 공백으로 구분 된 표현식입니다. 숫자는 속기를 포함하거나 포함하지 않을 수 있습니다. 샘플은 다음과 같습니다.

10 + 1b - 2k

산출

함수는 표현식의 평가를 숫자로 출력해야합니다. 출력이 너무 커서 표시하기에 과학적 표기법을 사용할 수 있습니다. 숫자가 정수가 아닌 경우 소수점 이하 세 자리 이상이어야합니다. 숫자가 정수인 경우 소수점 이하 자릿수를 유지하면 허용됩니다.

테스트 사례

입력

t

산출

1000000000000

입력

1 + 4b / 10k11

산출

399561.483

입력

e2 + k2ke-1 - b12

산출

-999799912

또는

-999799912.000

입력

142ek12

산출

142e1012

또는

142.000e1012

입력:

1.2m5.25

산출:

1200005.25

최종 노트

이것은 샌드 박스의 사용자의 도움으로 게시 된 첫 번째 도전입니다. 불분명 한 것이 있으면 저에게 알려주십시오. 명확히하기 위해 최선을 다하겠습니다.


1
좋은 첫 번째 도전
Digital Trauma

@DigitalTrauma 감사합니다! 답변을 기다리겠습니다.
cole

두 번째 예를 이해하지 못합니다. 나는 중간 용어가로 해석된다고 생각 1000 + 2000 * 10 ^ -1했지만, 그에 대한 최종 답을 -999998712얻었다. (또한, 제 해석은 규칙 4의 " 마지막 속기 "로 활기 차지 않지만 시퀀스를 이해하는 방법이 확실하지 않습니다 k2k.) 평가 단계를 설명해 주시겠습니까?
DLosc

@trichoplax 그렇습니다, 그것은 단지 숫자 여야합니다; 잘 잡는다.
cole

1
샌드 박스의 게시물에 댓글을보고 후, 나는 같은 예를 생각 2m2k같은 문자 번호를 - 어쩌면 "정수"- 또한 규칙 3의 논의에 추가해야합니다, 그것은 다른 용어를 사용하는 것이 가장 수 있습니다 123그 속기 는 아닙니다 . "숫자"라는 단어는 현재 약 3 개의 다른 정의를 가지고 있습니다.
DLosc

답변:


4

파이썬 2, 553 바이트

import sys
a=lambda i:lambda j:j*10**i
d={'k':a(3),'m':a(6),'b':a(9),'t':a(12)}
e='e'
o={'+':lambda i,j:i+j,'-':lambda i,j:i-j,'*':lambda i,j:i*j,'/':lambda i,j:i/j,e:lambda i,j:i*10**j}
r=[e,'*','/','+','-']
x=0
y=k=b=''
z=[]
q=lambda i,j:float(i or j)
for l in ''.join(sys.argv[1:]):
 if l in d:x,y=d[l](q(x,1)*q(y,1)),b
 elif l==e:z.extend([q(x+q(y,0),1),l]);x,y=0,b
 elif k==e:y+=l
 elif l in o:z.extend([x+q(y,0),l]);x,y=0,b
 else:y+=l
 k=l
z.append(x+q(y,0))
for m in r:
 while m in z:n=z.index(m);z[n-1:n+2]=[o[m](z[n-1],z[n+1])]
print repr(z[0])

이 질문은 조금 사랑받지 못하고 재미있어 보였으므로 나는 그것을 쐈다. 나는 코드 골프를 한 번도 해본 적이 없기 때문에 아마 향상 될 수있는 것이 많지만 언어에 대한 지식을 바탕으로 최선을 다했습니다. 파이썬 3에서는 1 바이트의 비용으로 동등한 솔루션을 사용할 수 있습니다 : print repr(z[0])-> print(repr(z[0])).

사용법은

python2 ShorthandMath.py <equation>

python2 ShorthandMath.py e2 + k2ke-1 - b12

출력

-999799912.0

이것을 개선하는 방법에 대한 입력은 대단히 감사하겠습니다. 충분한 관심이 있다면, 프로그램을 언 골프하고 논평 할 수 있지만, 대부분은 이미 읽기 쉽다 (코드 골프의 사실에 관한 것).

프로그램은 예제와 함께 중단됩니다. 142ek12그 값이 엄청나게 커지고 프로그램이 오버플로되기 때문에 .

보상하기 위해 다음이 약간 더 길지만 내장 임의 정밀도 라이브러리를 사용하여 이론적으로 발생하는 모든 것을 처리 할 수 ​​있습니다. 구문은 동일합니다.

Python 2, 589 588 바이트 (임의 정밀도)

import sys
from decimal import*
a=lambda i:lambda j:j*10**i
d={'k':a(3),'m':a(6),'b':a(9),'t':a(12)}
e='e'
o={'+':lambda i,j:i+j,'-':lambda i,j:i-j,'*':lambda i,j:i*j,'/':lambda i,j:i/j,e:lambda i,j:i*10**j}
r=[e,'*','/','+','-']
x=c=Decimal(0)
y=k=b=''
z=[]
q=lambda i,j:Decimal(float(i or j))
for l in ''.join(sys.argv[1:]):
 if l in d:x,y=d[l](q(x,1)*q(y,1)),b
 elif l==e:z.extend([q(x+q(y,0),1),l]);x,y=c,b
 elif k==e:y+=l
 elif l in o:z.extend([x+q(y,0),l]);x,y=c,b
 else:y+=l
 k=l
z.append(x+q(y,0))
for m in r:
 while m in z:n=z.index(m);z[n-1:n+2]=[o[m](z[n-1],z[n+1])]
print z[0]

첫 번째 버전은 괜찮을 것이라고 말하고 문제가있는 경우 다시 연락 드리겠습니다 (지금 너무 조심스럽게 보거나 생각할 수는 없습니다).
cole

@Cole Awesome, 감사합니다. 나는 주어진 모든 예에서 그것을 시험해 보았으며 적어도 모든 권리를 얻습니다.
BobChao87
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.