java - 优化字节数组简单模式匹配

标签 java pattern-matching arrays

为了练习,我不得不在字节数组中寻找特定的字节模式,这很简单,但我想知道是否可以简化甚至优化代码:

package anti_virus;

import java.nio.file.Files;
import java.nio.file.Paths;

public class Main {

    public static void main(String[] args) throws Exception {
        byte[] virus = Files.readAllBytes(Paths.get("C:/Users/Nick/Desktop/Uni/infected.com"));

        byte[] payload = new byte[]{0x56, 0x69, 0x72, 0x75, 0x73, (byte)0xB4, 0x40, (byte) 0xBB, 0x01,
                0x00, (byte) 0xB9, 0x05, 0x00, (byte) 0xBA, 0x0, 0x0, (byte) 0xCD, 0x21};

        // payload[14] and payload[14] have varying values

        for (int i = 0; i < virus.length; i++) {
            if ((virus[i] == payload[0]) && (virus[i+1] == payload[1]) && (virus[i+2] == payload[2]) &&
                (virus[i+3] == payload[3]) && (virus[i+4] == payload[4]) && (virus[i+5] == payload[5]) &&
                (virus[i+6] == payload[6]) && (virus[i+7] == payload[7]) && (virus[i+8] == payload[8]) &&
                (virus[i+9] == payload[9]) && (virus[i+10] == payload[10]) && (virus[i+11] == payload[11]) &&
                (virus[i+12] == payload[12]) && (virus[i+13] == payload[13]) && (virus[i+16] == payload[16]) &&
                (virus[i+17] == payload[17])) {
                  System.out.println("This file is probably a Virus!");
                  return;
            }
        }

        System.out.println("This file is no Virus.");
    }
}

最佳答案

是的,可以简化/优化:

  • 你可以使用 KMP algorithm (前 14 个字节)。该算法在 O(payload.length + virus.length) 中运行任意 payload 而不是 O(payload.length * virus.length) . (您的代码比 O(payload.length * virus.length) 更有效,原因只有一个:0x56 仅作为数组的第一个元素出现)<
  • 即使您选择保留算法,我也会使用循环来使代码更短且更易读。我还会修复循环中 ArrayIndexOutOfBoundsException 的来源(您可以访问索引 i, ..., i+13, i+16, i+17 virus 数组和你的循环条件允许 i 变得和 virus.length-1 一样大)。

关于java - 优化字节数组简单模式匹配,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30374471/

相关文章:

c++ - 使用二维数组创建矩阵

使用 CUDA 复制结构内的指针数组

javascript - 如何访问 Javascript 文件中的 JSON 数据

java - 艰巨的递归任务

java - 需要解决此正则表达式问题

list - 将 Scala 列表转换为另一种类型的列表

java - 识别文本文件中的 "figure"模式

java - 有效地将三个字母的货币名称转换为符号名称(例如 20 美元到 20 美元)

java - 将android抽屉导航与Android持久搜索库的搜索框相结合

java - Sonar - ArrayIndexOutOfBoundsException : 30344