Factura de agua de Fred

9

Fred es un tipo casi amigable, pero en realidad es malo.

Debido a esto, Fred vive solo en un pequeño apartamento en Los Altos, California. Fred es muy malo porque es muy particular con el agua. Él, por lo tanto, necesita su ayuda para determinar cuál es su factura de agua.

Su trabajo es escribir una función o programa que devuelva su factura de agua dada la cantidad de agua utilizada como entrada (que siempre es un número entero).

El consumo de agua viene en niveles. Esto significa que hay rangos de precios dependiendo de la cantidad de agua.

Estos son los niveles, sus precios y las cantidades de agua a las que corresponden:

Tier I
   First 10 Ccf: $3.8476/Ccf
Tier II
   Next 17 Ccf: $4.0932/Ccf
Tier III
   All subsequent water: $4.9118/Ccf

Para n cientos de pies cúbicos (Ccf), también existen los siguientes cargos adicionales:

CPUC fee: 1.5% of above charges
LIRA quantity surcharge: $0.047*n
PBOP amoritization surcharge: $0.004*n

La suma de las tarifas de Nivel I, Nivel II, Nivel III, CPUC, LIRA y PBOP es la factura total del agua. Esta suma debe devolverla o imprimirla en la consola redondeada a dos decimales.

Aquí hay dos ejemplos:

Input: 15
... Calculations which you do not need to output but here to help explain:
Tier I: 10*3.8476 = 38.476
Tier II: (15-10)*4.0932 = 20.466
Tier III: 0*4.9118 = 0
Tiers sum: 58.942
CPUC: 1.5% of 58.942 = 0.88413
LIRA: 0.047*15 = 0.705
PBOP: 0.004*15 = 0.06
Total sum: 58.942 + 0.88413 + 0.705 + 0.06 = 60.59113
...
Output: 60.59

Input: 100
... Calculations which you do not need to output but here to help explain:
Tier I: 10*3.8476 = 38.476
Tier II: 17*4.0932 = 69.5844
Tier III: (100-10-17)*4.9118 = 358.5614
Tiers sum: 466.6218
CPUC: 1.5% of  = 6.999327
LIRA: 0.047*100 = 4.7
PBOP: 0.004*100 = 0.4
Total sum: 478.721127
...
Output: 478.72

Este es el código de golf, ¡el código más corto en bytes gana!

Daniel
fuente
Comprueba que mi edición coincide con tu intención.
msh210
Sí, gracias @ msh210, eso es mucho más claro que lo que tenía
Daniel
Si está dispuesto a perder reputación en la votación negativa, ¿podría al menos explicar por qué?
Daniel
@Dopapp Es posible que a algunas personas no les guste el desafío. Nada que puedas hacer allí. Por lo que vale, los desafíos de votación negativa no restan la reputación del votante, solo las respuestas.
Mego
¿Tenemos que manejar no entero n?
PurkkaKoodari

Respuestas:

1

Pyth, 55 41 bytes

.R+s*Vv.",9t¬®Ï0NwÝ"lMcUQ,T27*.051Q2

El código contiene caracteres no imprimibles, así que aquí hay un xxdhexdump.

00000000: 2e52 2b73 2a56 762e 222c 3904 1874 c2ac  .R+s*Vv.",9..t..
00000010: c2ae c280 c293 c38f 301c 4e77 c39d 226c  ........0.Nw.."l
00000020: 4d63 5551 2c54 3237 2a2e 3035 3151 32    McUQ,T27*.051Q2

Explicación

  1. ."…"es una cadena de empaquetado que contiene 3.8476,4.0932,4.9118.
  2. vevalúa eso a la tupla (3.8476, 4.0932, 4.9118). Estos son los precios de los niveles multiplicados con CPUC agregado.
  3. UQgenera la gama 0... n-1.
  4. c... ,T27divide ese rango en los índices 10 y 27, con listas vacías adicionales al final si el rango es demasiado corto.
  5. lM encuentra la longitud de cada parte, dando la cantidad de agua para cada nivel.
  6. *V multiplica eso por la tupla del paso 2 para obtener los precios de los niveles.
  7. s suma los resultados.
  8. +*Q.051Agrega la entrada multiplicada por 0.051, es decir, LIRA + PBOP.
  9. .R... 2redondea el resultado a 2 decimales.

Pruébalo en línea.

PurkkaKoodari
fuente
2

Mathematica 83 76 69 bytes

1.015{3.8476,.2456(b=Boole)[#>10],.8186b[#>27],51/1015}&~Array~#~Total~2~Round~.01&

Función anónima que construye una matriz de los tres niveles en la primera columna más el LIRA y el PBOP representados como un número de precisión arbitraria en la cuarta columna. Todo se multiplica por 1.015y todos los elementos de la matriz se suman y redondean .01. Como 51/1015*1.015será el deseado, 0.051la salida es exactamente tan precisa como la especificación en OP.

Una solución más corta, en 76 bytes , como he sugerido en mi comentario bajo la solución Perl

{3.956314,.249284(b=Boole)[#>10],.830879b[#>27]}&~Array~#~Total~2~Round~.01&

donde se 1.015tiene en cuenta los precios desde el principio y luego se agrega LIRA y PBOP en la parte superior del primer nivel.

73 bytes (pero soy reacio a actualizar mi recuento de bytes ya que esto está bastante cerca de la solución directa de Perl):

69 bytes - ah, qué diablos, el golf también tomó un poco de esfuerzo.

.01Round[395.6314#+{24.9284,83.0879}.(UnitStep[#-1]#&/@{#-10,#-27})]&

EDITAR con respecto al error de coma flotante
Las primeras tres iteraciones de mi respuesta son de hecho exactas en su representación decimal, ya que todos los coeficientes involucrados tienen representaciones decimales finales. Sin embargo, dado que los coeficientes son flotantes explícitamente, almacenados en binario y que tienen representaciones binarias sin terminación, las entradas lo suficientemente grandes comenzarán a acumular errores en los dígitos menos significativos de la representación binaria. Supongo que, cuando el flotador es tan grande, que cabe solo 3-4 dígitos a la derecha del punto decimal, podemos esperar errores de alrededor de 1 centavo. Vea a continuación una respuesta exacta .

72 bytes, algo inmune a las imprecisiones de flotación

.01Round[{3956314,249284,830879}.(UnitStep[#-1]#&)/@(#-{0,10,27})/10^4]&

La multiplicación por el líder .01se realiza en el último paso. Hasta ese punto, todos los cálculos se realizan con enteros. Esto significa que si .01se omite el, habrá un resultado exacto , pero expresado en centavos, en lugar de dólares. Por supuesto, la multiplicación por un flotador convierte todo en un flotador y, como se mencionó, debe ser lo suficientemente pequeño como para caber en 64 bits y aún así ser exacto .01.

LLlAMnYP
fuente
2

05AB1E, 64 58 51 bytes

0T27¹)vy¹‚ï{0è})¥•_ÄÄ™wu24@•2'.:7ô)ø€PO¹"5.1"*+ïTn/

Explicado

0T27¹)                                               # list of price brackets
      vy¹‚ï{0è})                                     # min of each with input
                ¥                                    # calculate deltas to get amounts within each bracket
                 •_ÄÄ™wu24@•2'.:7ô                   # list of price rates with CPUC included
                                  )ø                 # zip with amounts for each rate
                                    €PO              # multiply amounts by their rates and sum
                                       ¹"5.1"*+      # add LIRA/PBOP
                                               ïTn/  # round to 2 decimals

Pruébalo en línea

Emigna
fuente
1

Perl 5, 73 bytes

La solución obvia. 72 bytes, más 1 para en -nelugar de -e.

printf'%.2f',$_*3.956314+($_-10)*($_>10)*.249284+($_-27)*($_>27)*.830879

Guardado 5 bytes gracias a LLlAMnYP . ¡Gracias!

msh210
fuente
Re mi comentario anterior, esta edición realmente elimina los errores de coma flotante que tenía en el original.
LLlAMnYP
@LLlAMnYP, seguramente cualquier aproximación debe tener un error para un valor suficientemente alto de la entrada. Esperemos que ese límite sea lo suficientemente alto como para que al OP no le importe (porque es una cantidad irrazonable de agua para la residencia de una sola persona).
msh210
@ msh210 ¡No sabes la historia de Fred!
gato
No, porque estás multiplicando y agregando números con representación decimal finita. Por supuesto, cuando los representa como flotantes, pueden tener una representación binaria no tan buena. Entonces puede esperar errores cuando la representación flotante permite solo 3-4 dígitos a la derecha del decimal. Mi "respuesta de bonificación" al final de mi publicación supera esto, usando números enteros hasta el último paso (que convierte centavos a dólares). Si omitiera la multiplicación por .01, seguiría siendo precisa siempre que se pueda almacenar el entero.
LLlAMnYP
1

Oracle SQL 11.2, 151 bytes

SELECT ((DECODE(SIGN(:1-10),1,10,:1)*3.8476)+(DECODE(SIGN(:1-27),1,17,:1-10)*4.0932)+(DECODE(SIGN(:1-27),-1,0,:1-27)*4.9118))*1.015+:1*0.051 FROM DUAL;

Sin golf

SELECT ((DECODE(SIGN(:1-10),1,10,:1)*3.8476)+
       (DECODE(SIGN(:1-27),1,17,:1-10)*4.0932)+
       (DECODE(SIGN(:1-27),-1,0,:1-27)*4.9118))*1.015+
       :1*0.051
FROM DUAL
Jeto
fuente
Deshágase del espacio entre SELECTy ((DECODEpara guardar un byte. ¡Ahorre más de 10 bytes usando una tabla con nombre! 7 eliminando los dos puntos y usando un nombre de columna de un carácter más tres utilizando un nombre de tabla de un carácter.
Giacomo Garabello
@Giacomo Garabello: eliminar el espacio siempre devuelve nulo con sapo y devuelve un error con SQLDeveloper. El script de creación de tabla agrega más de 10 bytes.
Jeto
no tienes que agregar el script de creación ... mira aquí
Giacomo Garabello
1

JavaScript ES6, 77 bytes

x=>(x>27?(x-27)*4.985477+109.681:(x>10?(x-10)*4.1546+39.053:x*3.9053))+.051*x

Sin golf

f = x => {
  if (x > 27) {
    res = (x - 27) * 4.985477 + 109.681306
  } else if (x > 10) {
    res = (x - 10) * 4.154598 + 39.05314
  } else {
    res = x * 3.905314
  }
  return res + 0.051 * x
}

Factoraje en los coeficientes LIRA y PBOP. El 1.5% extra se agrega al final.

Probablemente no sea la solución más eficiente en términos de golf, pero algo diferente de la de Perl.

El error de coma flotante debe ocurrir con números más grandes y puede solucionarse agregando 1 o 2 bytes adicionales a cada coeficiente.

f=x=>(x>27?(x-27)*4.985477+109.681:(x>10?(x-10)*4.1546+39.053:x*3.9053))+.051*x

console.log(f(15))
console.log(f(100))
console.log(f(200000))

Hugo
fuente
No es necesario los ()s de todo el x>10?:, ?:asociados derecha a izquierda. Creo que también puede guardar algunos bytes multiplicando los paréntesis, por ejemplo, (x-10)*4.154598+39.05314igual a x*4.154598-41.54598+39.05314igual x*4.154598-2.49284.
Neil
1

R , 52 bytes

approxfun(c(0,10,27,10^6),c(0,39.56,111.06,5036475))

Pruébalo en línea!

Genera una función de aproximación lineal, basada en los valores de mi respuesta anterior en 0,10,27 y 10 ^ 6. El problema: el límite superior en la entrada es 10 ^ 6.

approxfun(con ecdf, stepfun, splinefun, etc.) es una de las muchas características interesantes de R.

JayCe
fuente
0

VBA, 88 bytes

Function W(V):W=Round(.051*V+.203*(V*19.238-(V-10)*(V>10)*1.228-(V-27)*(V>27)*4.093),2)
 

La tasa base y las tasas diferenciales de uso más altas se han multiplicado por 5, y el multiplicador de tarifas de CPUC dividido por 5 (0,203).

El editor de VB agregará una End Functionlínea, por lo que se incluye el avance de línea de terminal.

Joffan
fuente
0

Pyth - 58 51 bytes

.Rs+*Bs*V++m3.8476Tm4.0932 17m4.9118Qm1Q.015*.051Q2

Test Suite .

Maltysen
fuente