Creación de un intervalo de fechas a partir de una sola fecha

En ocasiones, los intervalos de tiempo no se almacenan de forma explícita con un principio y un final. En su lugar, están implícitos solo por un campo: la fecha/hora del cambio.

Podría ser como en la tabla a continuación, en la que hay tipos de cambio para múltiples divisas: Cada cambio de tasa de divisa está en su propia fila, cada una de ella con una nueva tasa de conversión. Asimismo, la tabla contiene filas con fechas vacías que corresponden a la tasa de conversión inicial, antes de que se hiciera el primer cambio.

Tipos de cambio
Moneda Fecha de cambio Tasa
EUR - 8.59
EUR 28/01/2013 8.69
EUR 15/02/2013 8.45
USD - 6.50
USD 10/01/2013 6.56
USD 03/02/2013 6.30

Esta tabla define un conjunto de intervalos que no se superponen, donde los datos de inicio se llaman “Change Date” y la fecha de finalización se define por el comienzo del siguiente intervalo. Pero, ya que la fecha de finalización no se almacena de forma explícita en su propia columna, necesitamos crear esta columna para que la nueva tabla se convierta en una lista de intervalos.

En este ejemplo de script la tabla In_Rates la crea una sentencia inline load. Asegúrese de que las fechas en la columna Change Date estén en el mismo formato que el formato de fecha local.

In_Rates: LOAD * Inline [ Currency,Change Date,Rate EUR,,8.59 EUR,28/01/2013,8.69 EUR,15/02/2013,8.45 USD,,6.50 USD,10/01/2013,6.56 USD,03/02/2013,6.30 ];

Haga lo siguiente:

  1. Determine con qué rango de fechas desea trabajar. El inicio del rango debe ser anterior a la primera fecha de los datos, y el final del rango debe ser posterior a la última.

    Let vBeginTime = Num('1/1/2013');
    Let vEndTime = Num('1/3/2013');
    Let vEpsilon = Pow(2,-27);
  1. Cargue los datos de origen, pero cambie las fechas vacías en el principio del rango definido en el punto anterior. La fecha de cambio debe cargarse como “From Date”.

    Ordene la tabla primero por Currency, después conforme a “From Date” descendente, de modo que tenga las últimas fechas en la parte superior.

    Tmp_Rates:
    LOAD Currency, Rate,
    Date(If(IsNum([Change Date]), [Change Date], $(#vBeginTime))) as FromDate
    Resident In_Rates;
  2. Ejecute un segundo pase a través de los datos donde calcula el “To Date”. Si el registro actual tiene una moneda (currency) diferente del registro anterior, entonces es el primer registro de una nueva moneda (pero su último intervalo), por lo que deberá usar el final del rango definido en el paso 1. Si es la misma moneda (currency), debe tomar el “From Date” del registro anterior, restar una pequeña cantidad de tiempo y usar este valor como “To Date” en el registro actual.

    Rates:
    LOAD Currency, Rate, FromDate,
    Date(If( Currency=Peek('Currency'),
    Peek('FromDate') - $(#vEpsilon),
    $(#vEndTime)
    )) as ToDate
    Resident Tmp_Rates
    Order By Currency, FromDate Desc;
  3. Abandone la tabla de entrada y la tabla temporal.

    Drop Table Tmp_Rates;

El script mostrado a continuación actualizará la tabla de origen de la siguiente forma:

Tabla fuente actualizada
Moneda Rate FromDate ToDate
EUR 8.45 15/02/2013 vEndTime
EUR 8.69 28/01/2013 14/02/2013 23:59:59
EUR 8.59 vBeginTime 28/01/2013 23:59:99
USD 6.30 03/02/2013 vEndTime
USD 6.56 10/01/2013 2/02/2013 23:59:59
USD 6.50 vBeginTime 9/01/2013 23:59:59

Cuando se ejecute el script, tendrá una tabla que muestra los intervalos correctamente. Utilice la sección Vista previa del visor del modelo de datos para ver la tabla resultante.

Vista previa de datos
Moneda Rate FromDate ToDate
EUR 8.45 15/02/2013 01/03/2013
EUR 8.69 28/01/2013 14/02/2013
EUR 8.59 01/01/2013 28/01/2013
USD 6.30 03/02/2013 01/03/2013
USD 6.56 10/01/2013 2/02/2013
USD 6.50 01/01/2013 9/01/2013

Esta tabla se puede usar posteriormente en una comparación con una fecha existente usando los métodos Intervalmatch.

Example:  

El aspecto total del script Qlik Sense será el siguiente:

Let vBeginTime = Num('1/1/2013');
Let vEndTime = Num('1/3/2013');
Let vEpsilon = Pow(2,-27);
 
In_Rates: LOAD * Inline [ Currency,Change Date,Rate EUR,,8.59 EUR,28/01/2013,8.69 EUR,15/02/2013,8.45 USD,,6.50 USD,10/01/2013,6.56 USD,03/02/2013,6.30 ];
 
 
Tmp_Rates:
LOAD Currency, Rate,
Date(If(IsNum([Change Date]), [Change Date], $(#vBeginTime))) as FromDate
Resident In_Rates;
 
Rates:
LOAD Currency, Rate, FromDate,
Date(If( Currency=Peek('Currency'),
Peek('FromDate') - $(#vEpsilon),
$(#vEndTime)
)) as ToDate
Resident Tmp_Rates
Order By Currency, FromDate Desc;
 
Drop Table Tmp_Rates;