如何保存sql中的最后一个检查点以用于下一行

时间:2016-05-04 06:50:47

标签: sql vertica

有什么方法可以存储最后一次迭代的行结果并将其用于下一行迭代?

例如,我有一张表(Time_Table)。

__   Key   type   timeStamp             
1 )    1     B    2015-06-28 09:00:00  
2 )    1     B    2015-06-28 10:00:00  
3 )    1     C    2015-06-28 11:00:00  
4 )    1     A    2015-06-28 12:00:00  
5 )    1     B    2015-06-28 13:00:00  

现在假设我有一个90分钟的exceptionTime是不变的。 如果我开始检查我的Time_Table,那么:

  1. 第一行,因为09:00:00,之前没有行,它会直接将此记录放入我的目标表中。现在我的参考点是9:00:00。

  2. 对于10:00:00,的第二行,最后一个参考点为09:00:00,而TIMESTAMPDIFF(s,09:00:00,10:00:00)为60,小于所需的90.我不会将此行添加到我的目标表。

  3. 对于第三行,最后记录的异常位于09:00:00TIMESTAMPDIFF(s,09:00:00,11:00:00)为120,大于所需的90,因此我选择此记录并将参考点设置为{{ 1}}。

  4. 对于第四行11:00:00。同样,它也不会被保存。

  5. 再次保存此内容。

  6. 目标表

    TIMESTAMPDIFF(s,11:00:00,12:00:00)

    有什么方法可以解决这个问题__ Key type timeStamp 1 ) 1 B 2015-06-28 09:00:00 2 ) 1 C 2015-06-28 11:00:00 3 ) 1 B 2015-06-28 13:00:00

    我的方法:

    purely in SQL

    但这实际上并不起作用。

2 个答案:

答案 0 :(得分:2)

在Vertica中仅使用纯SQL是不可能的。要在纯SQL中执行此操作,您需要能够执行Vertica产品不支持的递归查询。在其他数据库产品中,您可以使用WITH子句执行此操作。对于Vertica,您将不得不在应用程序逻辑中执行此操作。这基于语句“查询块中的每个WITH子句必须具有唯一名称。尝试在同一查询块中对WITH子句查询名称使用同名别名会导致错误.WE子句不支持INSERT,DELETE,和UPDATE语句,你不能递归地使用它们“来自Vertica 7.1.x documentation

答案 1 :(得分:0)

肯定是,(不是在纯SQL中)使用LAG(since 7.1.x)取决于您使用的Vertica版本 或创建自定义UDx(用户定义的扩展)

Java中的UDx访问上一行,其行为与LAG相同,只有一步(hastag#performance)  (github full of udx examples

public class UdxTestFactory extends AnalyticFunctionFactory {

    @Override
    public AnalyticFunction createAnalyticFunction(ServerInterface srvInterface) {
        return new Test();
    }

    @Override
    public void getPrototype(ServerInterface srvInterface, ColumnTypes argTypes,
                             ColumnTypes returnType) {
        argTypes.addInt();
        argTypes.addInt();
        returnType.addInt();
    }

    @Override
    public void getReturnType(ServerInterface srvInterface, SizedColumnTypes argTypes,
                              SizedColumnTypes returnType) throws UdfException {
        returnType.addInt();
    }

    private class Test extends AnalyticFunction {

        @Override
        public void processPartition(ServerInterface srvInterface, AnalyticPartitionReader inputReader, AnalyticPartitionWriter outputWriter)
                throws UdfException, DestroyInvocation {

            SizedColumnTypes inTypes = inputReader.getTypeMetaData();
            ArrayList<Integer> argCols = new ArrayList<Integer>();

            inTypes.getArgumentColumns(argCols);

            outputWriter.setLongNull(0);

            while (outputWriter.next()) {
                long v1 = inputReader.getLong(argCols.get(0)); // previous row
                inputReader.next();
                long v2 = inputReader.getLong(argCols.get(0)); // curent row
                outputWriter.setLong(0, v2 - v1);
            }
        }

    }


}

编译&amp;将编译的类合并到单个jar中,为简单起见将其命名为TestLib.jar

$ javac -classpath /opt/vertica/bin/VerticaSDK.jar /opt/vertica/sdk/BuildInfo.java UdxTestFactory.java -d . 
$ jar -cvf TestLib.jar com/vertica/sdk/BuildInfo.class com/vertica/JavaLibs/*.class

加载库&amp;功能

CREATE OR REPLACE LIBRARY TestFunctions AS '/home/dbadmin/TestLib.jar' LANGUAGE 'JAVA';
CREATE OR REPLACE ANALYTIC FUNCTION lag1 AS LANGUAGE 'java' NAME 'com.vertica.JavaLibs.UdxTestFactory' LIBRARY TestFunctions;

并且..使用它

SELECT 
    lag1(col1, null) OVER (ORDER BY col2) AS col1_minus_col2 
FROM ...