Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/algorithm/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Algorithm 在列表中查找使图像唯一的像素,可以改进暴力吗?_Algorithm_Language Agnostic_Image Processing_Brute Force - Fatal编程技术网

Algorithm 在列表中查找使图像唯一的像素,可以改进暴力吗?

Algorithm 在列表中查找使图像唯一的像素,可以改进暴力吗?,algorithm,language-agnostic,image-processing,brute-force,Algorithm,Language Agnostic,Image Processing,Brute Force,假设我有一个字符串列表,其中每个字符串都是 正好4个字符长 在列表中是唯一的 对于这些字符串中的每一个,我想确定字符串中使字符串唯一的字符的位置 所以对于一个包含三个字符串的列表 abcd abcc bbcb 对于第一个字符串,我想识别第四个位置d中的字符,因为在任何其他字符串中,d不会出现在第四个位置 对于第二个字符串,我想识别第四个位置c中的字符 对于第三个字符串,我想识别第1个位置b的字符和第4个位置的字符,也是b 这可以简明扼要地表示为 abcd -> ...d abcc -

假设我有一个字符串列表,其中每个字符串都是

  • 正好4个字符长
  • 在列表中是唯一的
对于这些字符串中的每一个,我想确定字符串中使字符串唯一的字符的位置

所以对于一个包含三个字符串的列表

abcd
abcc
bbcb
对于第一个字符串,我想识别第四个位置d中的字符,因为在任何其他字符串中,d不会出现在第四个位置

对于第二个字符串,我想识别第四个位置c中的字符

对于第三个字符串,我想识别第1个位置b的字符和第4个位置的字符,也是b

这可以简明扼要地表示为

abcd -> ...d
abcc -> ...c
bbcb -> b..b

如果你考虑同一个问题,但是用一个二进制数列表

0101
0011
1111
那么我想要的结果就是

0101 -> ..0.
0011 -> .0..
1111 -> 1...
根据二进制主题,我可以使用XOR来识别两个二进制数中的唯一位

0101 ^ 0011 = 0110
我可以解释为,在这种情况下,第2位和第3位(从左到右读取)在这两个二进制数之间是唯一的。除非能以某种方式扩展到更大的列表中,否则这种技术可能是一种转移注意力的方法

蛮力方法是依次查看每个字符串,并让每个字符串遍历列表中其余字符串的垂直切片

那么名单呢

abcd
abcc
bbcb
我会从

abcd
并在垂直切片中进行迭代

abcc
bbcb
这些垂直切片会在哪里

a | b | c | c
b | b | c | b
或以列表形式,“ab”、“bb”、“cc”、“cb”

这将导致四个比较

a : ab -> . (a is not unique)
b : bb -> . (b is not unique)
c : cc -> . (c is not unique)
d : cb -> d (d is unique)
或者简明扼要地

abcd -> ...d
也许这是一厢情愿的想法,但我觉得应该有一个优雅而通用的解决方案,适用于任意大的字符串(或二进制数)列表。但如果有,我还没能看到

我希望使用此算法从一组唯一图像(位图)中获得最小签名,以便在将来有效地识别这些图像。如果未来的效率不是一个问题,我会使用每个图像的简单哈希

你能改进暴力吗

编辑 我喜欢的方法是将像素映射到图像

sprawl[Tuple<x=10, y=33,color=f1fefd>] => {
     image17,
     image23,
     ...
}

sprawl[Tuple<x=10, y=34,color=f1fef0>] => {
     image11
     ...
}
sprawl[Tuple]=>{
图17,
图23,
...
}
扩展[元组]=>{
图11
...
}
然后使用该映射来识别每个图像的最小特征像素集

如果一个像素(由x、y、颜色标识)只引用一个图像,那么我已经找到了该图像的完美(最小)特征

如果一个图像没有唯一的像素,情况会更复杂,但是因为我知道列表中的所有图像都是唯一的,所以我应该能够组合两个或多个像素引用(但尽可能少)来推断图像

更新


我一直在为这个做一个算法。我的问题非常类似于,我把我的算法写成了一个例子。此更新是为了标记仍在关注的任何人的注意(我看到五个书签)。我正在孤立地研究这个问题,所以欢迎任何和所有的反馈,即使只是为了观察我还没有说清楚

您可以生成一个二维数组,其中包含每个字符在每个位置出现的次数(0-3)。例如,
arr[1,3]
将包含数字/字符
1
出现在最后位置的次数

然后,对于每个字符串
s
,检查字符串中的所有字符。根据数组,在该位置只出现一次的字符是该字符串的唯一字符。换句话说,如果
arr[s[i],i]==1
,则字符串
s
i
位置是唯一的


这将为您提供线性时间的解决方案,而您提供的算法将需要二次时间。

如果您的目标是以后识别图像,您可以通过拾取预定义的点作为标识像素来创建图像的快速散列

例如,您可以有如下结构(类、struct,不管是哪种语言):

structure ImageHash {
    int x_pixels, y_pixels;
    u_long hash;
    void createHash(Image img) {
        x_pixels = img.x_pixels;
        y_pixels = img.y_pixels;
        for(int i = 1; i < 5; i++) {
            int x = x_pixels / i;
            for(int j = 1; j < 5; j++) {
                int y = y_pixels / j;
                int r = img.getPixelRed(x,y);
                int g = img.getPixelGreen(x,y);
                int b = img.getPixelBlue(x,y);
                hash = (hash * 31) ^ (r^g^b);
            }
        }
    }
}
structure-ImageHash{
整数x_像素,y_像素;
乌龙杂烩;
void createHash(图像img){
x_像素=img.x_像素;
y_像素=img.y_像素;
对于(int i=1;i<5;i++){
int x=x_像素/i;
对于(int j=1;j<5;j++){
int y=y_像素/j;
int r=img.getPixelRed(x,y);
int g=img.getPixelGreen(x,y);
intb=img.getpixelbue(x,y);
散列=(散列*31)^(r^g^b);
}
}
}
}
这种“不完全散列”将允许您识别可能的身份,然后您可以根据需要节省昂贵的、完整的比较


根据需要展开不完整的哈希。

此问题可以通过trie或前缀树解决

对于示例中的3个字符串:

abcd
abcc
bbcb
将转换为trie树(其中^表示树的根):

它分支的节点的路径是公共前缀。最后一个分支点之后的节点是使特定字符串唯一的节点。在这种情况下,它们是d,c,b

我假设字符串的顺序对您来说并不重要,您可以比较所有字符串以找到唯一性,而不仅仅是相邻的字符串


复杂度应该是O(nxm)。但这可能会受到字符串中字符域的影响。

如果将bbcd添加到列表中,则某些项目将没有唯一字符。这会对你的目标产生什么影响?@Kathy如果是那样的话,我就无法得到我想要的签名。对于我希望使用此算法的应用程序,这种情况是可能的,但不太可能发生。@Ed Guinness,您能否描述一下“在将来更有效地识别图像”部分
^--a-b-c-d
 \      \
  \      c
   \
    b-b-c-b