Creación de tablas en Envision


Inicio » Recursos » Aquí

Si bien el modo más habitual de crear una tabla en Envision consiste en la lectura de la tabla desde archivos planos, Envision también ofrece la posibilidad de crear tablas por sí solo. Para mayor precisión, estas tablas creadas pueden definirse e instanciarse dentro del script. La creación de una tabla puede ser particularmente útil cuando ninguna de las tablas de entrada contiene las propiedades que se buscan para un cálculo específico.


Resumen de la sintaxis

La sintaxis habitual para crear una tabla yace en las instrucciones table y extend, que se representan en esta sintaxis:
table T = extend.range(Orders.42)
Aquí, la palabra clave table no debería confundirse con el tipo de mosaico, como en show table. La tabla T puede utilizarse en el script del mismo modo que en cualquier tabla normal cargada desde archivos.
show table "Number of lines" with sum(T.1)

extend.range()

El modo más sencillo de crear una tabla es utilizando la extensión de intervalo extend.range(): para cada línea de tabla original, se crean y se numeran N líneas. La extensión de intervalo puede ser útil cuando se busca introducir nuevas líneas en una tabla.

La sintaxis es la siguiente:
table T = extend.range(Orders.K)
T.Quantity = Orders.Quantity // proyección implícita
show table "Line numbers" with T.N, T.Quantity
Se espera que el argumento sea un entero, que puede variar de una línea a otra en la tabla original. Esto proporciona control de la granularidad de la cantidad de líneas que deben introducirse.

La tabla T se escribe como una extensión de la tabla que se especificó originalmente como argumento. Por lo tanto, como se ilustra en la línea 2 más arriba, las asignaciones entre tablas planas funcionan porque cada línea de T sigue estando asociada con su contrapartida originaria en Orders. El campo T.N se rellena por defecto y puede representar cualquier número de línea. Este campo comienza en 1 y aumenta en incrementos de +1.

Tenga cuidado: la función extend.range() puede generar una cantidad arbitrariamente grande de líneas. En primer lugar, es probable que la generación de una tabla extremadamente grande resulte muy lenta; en segundo lugar, de acuerdo con el límite de procesamiento de su cuenta de Lokad, puede no resultar exitosa. En la práctica, si K es mayor que 10 sobre el promedio, extend.range() puede no ser la solución adecuada para el problema que intenta resolver.

El ejemplo a continuación ilustra cómo pueden duplicarse líneas específicas dentro de una tabla preservando al mismo tiempo el contenido original de esta.
read "/sample" all
expect Grid[*]

table G = extend.range(Grid.Min == 0 ? 2 : 1)
G.Min = Grid.Min // afinidad entre 'G' y 'Grid'
G.Max = Grid.Max
G.Probability = Grid.Probability
G.Probability = 0 where G.N == 2
show table "My Grid" with Id, G.Probability, G.Min, G.Max

extend.distrib()

Las distribuciones de Envision ofrecen un álgebra potente, que puede utilizarse para evitar los cálculos complicados de probabilidades en listas. Sin embargo, existen situaciones en las que tener una lista de probabilidades sin procesar es adecuado e incluso deseable. La extensión de distribución extend.distrib() convierte a un vector de distribuciones en una tabla, como lo ilustra la sintaxis a continuación:
table T = extend.distrib(D)
show table "Distribution details" with Id, T.Min, T.Max, T.Probability
Se espera que el argumento D sea un vector de distribuciones, como habitualmente lo genera el motor de pronóstico probabilístico de Lokad. La tabla T es escribe como una extensión de las tablas originarias, la tabla Items implícita en el script anterior. La tabla T se rellena con tres campos:

  • T.Min: El límite inferior integral inclusivo del segmento
  • T.Max: el ĺimite superior integral inclusivo del segmento
  • T.Probability: la suma de la distribución sobre el intervalo inclusivo

A pesar de su nombre, el campo Probability alude en realidad a la suma de la distribución sobre el intervalo de depósito que se devuelve.

Para distribuciones relativamente compactas, los segmentos tienen una longitud de 1 y, por lo tanto, T.Min == T.Max. Sin embargo, si la distribución abarca valores más altos, los segmentos de longitud igual a 1 acabarían generando posiblemente millones de líneas, algo que se vuelve imposible de gestionar. Por lo tanto, al enfrentarse a distribuciones con valores tan grandes, Envision autoagrega las distribuciones en torno a segmentos más grandes. Los algoritmos se adaptan de consecuencia para mantener la dimensión de las tablas generadas dentro de parámetros gestionables.

Por diseño, extend.distrib() siempre identifica el segmento cero. Como resultado, el segmento [0;0] siempre obtiene su propia línea en la tabla generada. Este comportamiento es útil en muchas situaciones de negocios en las que la demanda cero representa un caso extremo, como una cobertura de existencias infinita, que requiere una lógica específica.

Luego, se proporcionan otras tres sobrecargas para extend.distrib() para obtener más control sobre la granularidad específica de la tabla generada. La primera sobrecarga está pensada para ayudar a construir una lista de priorización de compra al tiempo que tiene en cuenta los niveles de stock actuales. La sintaxis es la siguiente:

Brecha (Gap)

La primera sobrecarga tiene como objetivo ayudar a crear la lista de priorización de compra teniendo en cuenta los niveles de stock al mismo tiempo. La sintaxis es la siguiente:
table T = extend.distrib(D, S)
El primer argumento D es el mismo que se definió anteriormente. Se espera que el segundo argumento S sea un número entero. Cuando este segundo argumento está presente, la tabla generada siempre incluye dos líneas dedicadas a los dos segmentos [0;0] y [1;S]. Como se mostraba antes, se autogeneran más segmentos comenzando desde S+1.Cuando no se especifica, el valor predeterminado de este argumento es cero.

En la práctica, el argumento S a menudo se define como la suma del stock disponible más el stock pedido. De hecho, al reordenar, solo deberían considerarse las probabilidades de demanda que exceden el nivel de stock actual.

Multiplicador (Multiplier)

La segunda sobrecarga está pensada para situaciones que involucran multiplicadores de lotes. En estas situaciones, la tabla debería iterar sobre segmentos de dimensiones específicas. La sintaxis es la siguiente:
table T = extend.distrib(D, S, M)
Los argumentos D y S son los que se definieron anteriormente. Se espera que el tercer argumento, M, sea un número entero, que representa la longitud del segmento deseada. Así, la tabla incluye la lista de segmentos [0;0], [1;S], [S+1;S+M] [S+M+1;S+2M] … Si M es cero, la función recurre al dimensionamiento automático de los segmentos.

En la práctica, el forzado de los segmentos de longitud 1 probablemente generaría problemas de rendimiento, debido a que la dimensión de la tabla podría resultar arbitrariamente grande. Así, Envision puede, en cambio, valerse de un múltiplo de M. El uso de un múltiplo asegura que la lógica de multiplicador de lote siga funcionando, al tiempo que se preservan límites sensatos en el número de líneas por generar.

Como regla general, le sugerimos no utilizar esta sobrecarga a menos que haya multiplicadores de lotes involucrados; y cuando así fuera, se recomienda mantener M en cero para todo artículo que no tenga un multiplicador de lote específico.

Alcance (Reach)

La tercera sobrecarga está pensada para situaciones que involucran MOQ. En estas situaciones, la tabla debería iterar lo suficiente como para alcanzar determinados valores deseados. La sintaxis es la siguiente:
table T = extend.distrib(D, S, M, R)
Los argumentos D, S y M son los que se definieron anteriormente. Se espera que el cuarto argumento, R, sea un número entero no negativo. Representa el valor máx que se desea alcance la grilla, es decir, habrá una línea en la que T.Max es mayor o igual que R. Cuando no se especifica, el valor predeterminado de este argumento es cero.

En la práctica, este argumento se utiliza para gestionar limitaciones grandes de cantidades de pedido mínimas (MOQ) que solo pueden satisfacerse si la tabla generada itera valores distantes para cubrir los valores de MOQ.

Como regla general, sugerimos no utilizar esta sobrecarga a menos que haya MOQ que alcanzar. Y cuando sea así, se sugiere mantener R lo menor posible. Un valor R pequeño no evita que la tabla T alcance valores mayores, solo asegura que se alcancen valores más grandes.

extend.billOfMaterials()

La lista de materiales cubre situaciones en las que el interés no reside en los artículos que han sido vendidos o proporcionados, sino en sus piezas o su composición. En esas situaciones, es recomendable traducir el historial de demanda a nivel de artículo a un historial de demanda a nivel de piezas. La traducción se controla a través de la lista de materiales, que especifica la composición de cada artículo.

La función llamada extend.billOfMaterials() está diseñada precisamente para cubrir este caso de uso con:
table T = extend.billOfMaterials(
Item: J.Id
Part: B.PartId
Quantity: B.Quantity
DemandId: O.OrderId
DemandValue: O.Quantity)

T.DemandDate by T.DemandId = same(O.Date) by O.OrderId // ilustra cómo obtener la fecha

show table "Details" with Id, T.DemandDate, T.Quantity
Se espera que haya tres tablas:J, B y O. La tabla J generalmente es la tabla de artículos, pero no es un requisito obligatorio. La tabla B está pensada como la tabla de la lista de materiales y se espera que sea una extensión de la tabla J, es decir, de tipo (Id, *) cuando J es la tabla de artículos. Se espera que la tabla O sea el historial de demanda, generalmente aludiendo a la tabla de pedidos. También se espera que la tabla O sea una extensión de la tabla J.

La tabla resultante es una extensión de la tabla J, con las afinidades correspondientes. La tabla T contiene dos campos ya completos:
  • T.DemandId, que está pensada para ofrecer un modo de identificar en la tabla T las líneas que se originan en la tabla O.
  • T.Quantity, que se obtiene implementando la lista de materiales.

A menudo, resulta útil introducir una fecha en la tabla T. Esto puede realizarse con una instrucción "left-by" como se ilustra en la línea debajo del bloque billOfMaterials() más arriba.

La función extend.billOfMaterials() admite ensamblados recursivos, es decir, un artículo puede aparecer como componente o como paquete dentro de la tabla B. Naturalmente, la función falla con un error si se encuentran dependencias cíclicas en la tabla de la lista de materiales.

El argumento Quantity representa el número de unidades de B.PartId involucradas al vender o proporcionar un conjunto identificado por J.Id.