Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/sorting/2.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
Graphics 在一维中对颜色列表进行排序?_Graphics_Sorting_Colors - Fatal编程技术网

Graphics 在一维中对颜色列表进行排序?

Graphics 在一维中对颜色列表进行排序?,graphics,sorting,colors,Graphics,Sorting,Colors,我想对一维的颜色列表进行排序,这样一个典型的人类会认为彼此“相似”的颜色彼此接近 显然,这是一个很难或可能不可能做到“完美”的问题,因为颜色通常是用三维来描述的,但这并不意味着没有一些排序方法看起来比其他方法更自然 例如,按RGB排序效果不太好,因为它将按以下顺序排序,例如: (1) R=254 G=0 B=0 (2) R=254 G=255 B=0 (3) R=255 G=0 B=0 (4) R=255 G=255 B=0 也就是说,它将交替那些颜色红、黄、红、黄,这两种“红”本质上是不可想象

我想对一维的颜色列表进行排序,这样一个典型的人类会认为彼此“相似”的颜色彼此接近

显然,这是一个很难或可能不可能做到“完美”的问题,因为颜色通常是用三维来描述的,但这并不意味着没有一些排序方法看起来比其他方法更自然

例如,按RGB排序效果不太好,因为它将按以下顺序排序,例如:

(1) R=254 G=0 B=0 (2) R=254 G=255 B=0 (3) R=255 G=0 B=0 (4) R=255 G=255 B=0

也就是说,它将交替那些颜色红、黄、红、黄,这两种“红”本质上是不可想象的不同,这两种黄色也不可想象的不同

但总的来说,HLS排序的效果要好得多,我认为HSL甚至比这更好;无论是哪一种,红色都将彼此相邻,黄色将彼此相邻

但HLS/HSL也存在一些问题;人们认为是“黑色”的东西可以彼此分开,人们认为是“白色”的东西也可以分开

再一次,我明白,我几乎不得不接受这样的分裂;我只是想知道是否有人找到了比HLS/HSL更好的方法。我知道“更好”有点武断;我的意思是“对一个典型的人来说更自然”

例如,我曾经有过一个模糊的想法,但还没有尝试过,可能是“L是最重要的东西,如果它是非常高或非常低的”,但除此之外,它是最不重要的。有人试过这个吗?效果好吗?您认为“非常低”和“非常高”的具体含义是什么?等等或者有人发现了其他可以改善HSL的东西吗

我还应该注意到,我知道我可以通过颜色的立方体定义一条空间填充曲线,并对它们进行一维排序,因为它们在沿着该曲线行进时会遇到。这将消除可感知的不连续性。然而,这并不是我真正想要的;比起完美的小规模分组,我更想要像样的整体大规模分组


提前感谢您的帮助。

您可以采取两种方法。简单的方法是将每种颜色提取为一个值,然后对值列表进行排序。复杂的方法将取决于您必须排序的所有颜色;也许这将是一个迭代的解决方案,反复洗牌周围的颜色,试图尽量减少整个序列的“能量”

我的猜测是,你想要一些简单、快速、看起来“足够好”的东西(而不是试图找出“最佳”的美学颜色),因此简单的方法对你来说就足够了

我认为HSL是一个不错的选择。差不多

sortValue = L * 5 + S * 2 + H

假设H、S和L都在[0,1]范围内。

经过几分钟的思考,我想到了一个想法。这可能是废话,也可能根本不起作用,但无论如何我都会把它吐出来

定义颜色空间上的距离函数,
d(x,y)
(其中输入
x
y
是颜色,输出可能是浮点数)。您选择的距离函数可能不太重要。它可能是R、G和B分量差值的平方和,也可能是H、L和S分量差值的多项式(分量的权重取决于你认为它们的重要性)

然后,计算列表中每种颜色之间的“距离”,这实际上为您提供了一个图形。接下来计算图的最小生成树。然后确定MST中存在的最长路径(没有回溯)。此路径的端点将是最终列表的端点。接下来,通过将路径上的“分支”中的点引入路径本身,尝试将树“展平”成一条直线


嗯。如果你的MST最终在颜色空间中变成一个近循环的形状,那么这可能不太管用。但是可能任何方法都会有这个问题。

如果不将3个颜色维度减少为一个测量值,就无法做到这一点。有许多(无限)方法可以减少此信息,但在数学上不可能这样做,即确保减少的连续统上彼此相邻的两个数据点在其所有三个分量颜色值中也彼此相邻。因此,这种类型的任何公式都可能最终将不同的颜色分组

正如您在问题中提到的,排序的一种方法是通过您试图排序的数据点所占据的三维颜色空间拟合复杂曲线,然后将每个数据点减少到其在曲线上的最近位置,然后减少到该点沿曲线的距离。这是可行的,但在每种情况下,它都是针对特定数据点集定制的解决方案(而不是普遍适用的解决方案)。它也会相对昂贵(也许),而且在一个数据集上根本无法工作,而这个数据集不是以曲线的方式很好地分布的

一个更简单的选择(不可能完美地工作)是选择两种“端点”颜色,最好是在色轮的相对侧。例如,您可以选择红色作为一种端点颜色,蓝色作为另一种端点颜色。然后将每个颜色数据点转换为从0到1的比例值,其中高度偏红的颜色将获得接近0的分数,高度偏蓝的颜色将获得接近1的分数。分数为0.5表示颜色中没有红色或蓝色(也称为绿色),或者红色和蓝色(也称为紫色)的数量相等。这种方法并不完美,但它是解决此问题的最佳方法
    public static int zValue(int r, int g, int b) {
            return split(r) + (split(g)<<1) + (split(b)<<2);
    }

    public static int split(int a) {
            // split out the lowest 10 bits to lowest 30 bits
            a=(a|(a<<12))&00014000377;
            a=(a|(a<<8)) &00014170017;
            a=(a|(a<<4)) &00303030303;
            a=(a|(a<<2)) &01111111111;
            return a;
    }
0.2126 * R + 0.7152 * G + 0.0722 * B
0.299 * R + 0.587 * G + 0.114 * B
sqrt(0.299 * R^2 + 0.587 * G^2 + 0.114 * B^2)