Diferencias con el ex4j original » Histórico » Versión 4
Federico Vera, 2018-08-06 22:05
Cache de evaluación
1 | 1 | Federico Vera | # Diferencias con el ex4j original |
---|---|---|---|
2 | |||
3 | {{>toc}} |
||
4 | # Nota |
||
5 | Existen muchas diferencias con `exp4j` original, algunas de las cuales pueden causar problemas de compatibilidad para usuarios avanzados de `exp4j`. |
||
6 | |||
7 | # Diferencias Generales |
||
8 | 2 | Federico Vera | Entre los cambios mas significativos de esta versión de `exp4j` se encuentran: un simplificador (preevaluador), manejo de variables, funciones adicionales, enums, [[Diferencias_con_el_ex4j_original#Constantes-como-funciones|*constantes como funciones*]] e impresión de tokens. |
9 | 1 | Federico Vera | |
10 | 2 | Federico Vera | ## Simplificador (preevaluador) |
11 | El simplificador es una funcionalidad intereante ([discusión original](https://github.com/fasseg/exp4j/issues/26)) cuando las expresiones tienen operaciones conocidas en tiempo de creación, por ejemplo, consideremos la expresión `2^x + 4 / 2` que puede convertirse en `2^x + 2`. No parece demasiado.... o si? la realidad es que al utilizar múltiples evaluaciones, muchas constantes varios valores de `x` (por ejemplo al graficar) esta diferencia es muy notoria ([primera prueba de performance](https://github.com/fasseg/exp4j/issues/26#issuecomment-70547026)). |
||
12 | 1 | Federico Vera | |
13 | 2 | Federico Vera | Otra simplificación interesante es al utilizar expresiones del tipo `if(exp, v_true, v_false)`, el simplificador puede quitar (en algunos casos) el bloque `if` completo, por ejemplo `if(1 > 0 & 3 < 4, a * pi(), e())` se convierte en `a * pi()` (de hecho en `if(1, a * pi(), e())`... _Todavía estoy trabajando en esto..._ |
14 | 1 | Federico Vera | |
15 | 2 | Federico Vera | ### Usando el simplificador |
16 | Por defecto se encuentra desactivado, dado que no es realmente necesarios cuando se ejecuta una operación una sola vez (el simplificador hace toda una evaluación para funcionar). |
||
17 | 1 | Federico Vera | |
18 | 2 | Federico Vera | Para activar el simplificador simplemente es necesario pasar `true` al builder: |
19 | 1 | Federico Vera | |
20 | ~~~java |
||
21 | 2 | Federico Vera | // por defecto ExpressionBuilder#build() es #build(false) |
22 | 1 | Federico Vera | Expression ex = new ExpressionBuilder("2^3 + 4 / 2").build(true); |
23 | double result = ex.evaluate(); |
||
24 | ~~~ |
||
25 | |||
26 | 2 | Federico Vera | ### Una pequeña nota |
27 | Un simplificador _**debería**_ simplificar solamente funciones determinísticas, por lo tanto ahora disponemos de una bandera `deterministic` en el constructor de las funciones (valor por defecto `true`). Por lo tanto si utiliza funciones [no deterministas](https://es.wikipedia.org/wiki/Algoritmo_no_determinista) deberá cambiar la declaración de la función a: |
||
28 | 1 | Federico Vera | |
29 | ~~~java |
||
30 | 2 | Federico Vera | Function rand_deterministica = new Function("randd", 0) { |
31 | 1 | Federico Vera | @Override |
32 | public double apply(double... args) { |
||
33 | 2 | Federico Vera | // Falla épica de simplificación |
34 | 1 | Federico Vera | return Math.random(); |
35 | } |
||
36 | }; |
||
37 | ~~~ |
||
38 | 2 | Federico Vera | A esto: |
39 | 1 | Federico Vera | ~~~java |
40 | 2 | Federico Vera | Function rand_NO_deterministica = new Function("randnd", 0, false) { |
41 | // Esta bandera ^^^^^ |
||
42 | 1 | Federico Vera | @Override |
43 | public double apply(double... args) { |
||
44 | return Math.random(); |
||
45 | } |
||
46 | }; |
||
47 | ~~~ |
||
48 | |||
49 | 2 | Federico Vera | Este cambio puede resultar molesto para aquellos que utlicen muchas funciones no deterministas... aunque dado que el simplificador está desactivado por defecto, la mayoría de la gente no debería tener problemas. |
50 | 1 | Federico Vera | |
51 | 3 | Federico Vera | ## Manejo interno de variables |
52 | Esto no es un cambio muy importante, la idea es mejorar un poco el rendimiento, evitar errores y generar un código mas legible. Pero no honra la filosofía de _inmutabilidad_ de las calculadoras basadas en stacks, así que si desea comenzar a hackear `exp4j` va a tener que tomar esto en cuenta. |
||
53 | 1 | Federico Vera | |
54 | 3 | Federico Vera | ### Entonces... ¿cuál es el cambio? |
55 | El cambio real es commit:d2d96fce y en commit:7f280988 puede verse una de las situaciones que se generan. |
||
56 | 1 | Federico Vera | |
57 | The original `exp4j` uses one token per variable, that's to say one token each time a variable is present in an expression which creates every time a variable is set, a state where the same variable has a different values in an expression. That's really a no go for me. |
||
58 | |||
59 | 3 | Federico Vera | Esta versión de `exp4j` usa el mismo token para todas las instancias de una variable en una expresión (en versiones anteriores existían situaciones en las que podía tenerse varios valores diferentes para una sola variable. |
60 | 1 | Federico Vera | |
61 | 3 | Federico Vera | ## Impresión de tokens |
62 | A partir de esta versión es posible imprimir la representación interna de una expresión. |
||
63 | 1 | Federico Vera | |
64 | 3 | Federico Vera | ### ¿Cómo? |
65 | Las dos formas básicas son: |
||
66 | 1 | Federico Vera | ~~~java |
67 | Expression exp = new ExpressionBuilder("2x + 1").variable("x").build(); |
||
68 | String out1 = exp.toString(); |
||
69 | // out1 -> 2.0 x * 1.0 + |
||
70 | String out2 = exp.toTokenString(); |
||
71 | // out2 -> NUMBER[2.0] VARIABLE[x] OPERATOR[*] NUMBER[1.0] OPERATOR[+] |
||
72 | ~~~ |
||
73 | |||
74 | ## Constantes como funciones |
||
75 | 3 | Federico Vera | Finalmente nos encontramos con el cambio que va a resultar mas molesto por algunos usuarios, y el que tiene mas probabilidades de _romper cosas_. En la verisión original de `exp4j` las constantes eran declaradas como variables inmutables, pero en esta versión de `exp4j` son declaradas como funciones, por lo tanto una expresión como `d * pi` pasa a ser `d * pi()`. |
76 | 1 | Federico Vera | |
77 | 4 | Federico Vera | ## Cache de evaluación |
78 | Se implementó #752 y el cache de evaluación está disponible. |
||
79 | |||
80 | 2 | Federico Vera | ## Traducciones |
81 | Todos los mensajes y advertencias pueden ser traducidos, y ya se tiene la primera traducción al Español |
||
82 | 1 | Federico Vera | |
83 | 2 | Federico Vera | ## Serialización |
84 | Todas las expresiones son `Serializable`s! |
||
85 | 1 | Federico Vera | |
86 | 2 | Federico Vera | ## Funciones adicionales |
87 | * [[Funciones Incluidas]] |
||
88 | * [[Operadores Incluidos]] |
||
89 | * [[Funciones y Operadores adicionales]] |