Java 比例编号为<;=255?
我有一些单元格,其数值可以是介于0和Java 比例编号为<;=255?,java,language-agnostic,math,distribution,Java,Language Agnostic,Math,Distribution,我有一些单元格,其数值可以是介于0和Integer.MAX\u value之间的任何值。我想对这些单元格进行相应的颜色编码 如果该值为0,则r=0。如果该值为整数.MAX_值,则r=255。但两者之间的价值又如何呢 我想我需要一个极限为x=>整数的函数。最大值是255。这个函数是什么?还是有更好的方法 我可以只做(value/(Integer.MAX\u value/255)),但这会导致许多低值为零。所以,也许我应该用一个log函数来实现它 我的大多数值都在[0,10000]范围内。因此,我想
Integer.MAX\u value
之间的任何值。我想对这些单元格进行相应的颜色编码
如果该值为0,则r=0。如果该值为整数.MAX_值
,则r=255。但两者之间的价值又如何呢
我想我需要一个极限为x=>整数的函数。最大值是255。这个函数是什么?还是有更好的方法
我可以只做(value/(Integer.MAX\u value/255))
,但这会导致许多低值为零。所以,也许我应该用一个log函数来实现它
我的大多数值都在[0,10000]范围内。因此,我想强调其中的差异
我可以只做(value/(Integer.MAX_value/255)),但这会导致许多低值为零
您可以采取的一种方法是使用模运算符(r=value%256;
)。虽然这不能确保Integer.MAX\u值
变成255,但它可以保证一个介于0和255之间的数字。它还允许在0-255范围内分配较低的数字
编辑:
有趣的是,当我测试这个时,Integer.MAX_值%256
确实会导致255
(我最初错误地测试了%255
,结果是错误的)。这似乎是一个非常直截了当的解决方案 您要查找的值是:r=255*(value/Integer.MAX\u value)。因此,您必须将其转换为双精度,然后再转换回整数。一般来说(因为我不清楚这是否是一个Java或语言不可知的问题),您可以将您的值除以整数。MAX_value
,乘以255
,然后转换为整数。这是可行的<代码>r=值/8421504代码>
8421504实际上是“魔法”数字,等于最大值/255。因此,MAX_VALUE/8421504=255(还有一些变化,但足够小的整数数学将消除它)
如果您想要一个没有幻数的,这应该可以工作(并且性能相同,因为任何好的编译器都会用实际值替换它:
r=value/(Integer.MAX_value/255);
好的方面是,这不需要任何浮点值。最公平的线性缩放实际上是这样做的:
floor(256 * value / (Integer.MAX_VALUE + 1))
请注意,这只是伪代码,并假定为浮点计算
如果我们假设Integer.MAX_值+1是2^31,并且/将给我们整数除法,那么它将简化为
value / 8388608
为什么其他答案是错误的
一些答案(以及问题本身)暗示了(255*value/Integer.MAX_value)
的变化。可能必须使用round()
或floor()
将其转换为整数
如果使用floor()
如果使用round()
使用我上面提到的缩放方法,不会出现这样的问题
非线性方法
如果要使用日志,请尝试以下操作:
255 * log(value + 1) / log(Integer.MAX_VALUE + 1)
您也可以只取值的平方根(这不会一直到255,但如果您愿意,可以将其放大)。最佳答案实际上取决于您想要的行为
如果您希望每个单元格的颜色通常与相邻单元格的颜色不同,请按照第二段中akf的说法使用模(x%256)
如果你想让颜色对实际值有一些影响(比如“蓝色意味着较小的值”一直到“红色意味着巨大的值”),你必须发布一些关于你期望的值分布的信息。因为你担心许多低值为零,我可能猜你有很多,但那只是一个猜测
在第二个场景中,您确实希望将可能的回答分为256个“百分位数”,并为每个“百分位数”指定一种颜色(每个百分位数中可能的回答数相等).对于0-2^32到0-255范围内的线性映射,只需获取高阶字节。以下是使用二进制&
和位移位的效果:
r = value & 0xff000000 >> 24
使用mod 256肯定会返回一个0-255的值,但您无法从结果中得出任何分组意义-1257、513、1025都将映射到缩放值1,即使它们彼此相距很远
如果希望在低值之间更具区分性,并将更多的大值合并在一起,则日志表达式将起作用:
r = log(value)/log(pow(2,32))*256
编辑:哎呀,我的高中代数老师Buckenmeyer夫人会晕倒的!log(pow(2,32))
与32*log(2)
相同,而且评估成本更低。现在我们还可以更好地考虑这一点,因为256/32是一个不错的8:
r = 8 * log(value)/log(2)
log(value)/log(2)
实际上是log-base-2的value
,这个log对我们来说非常简洁:
r = 8 * log(value,2)
好了,Buckenmeyer夫人-你的努力并没有完全白费!如果你抱怨低数值变为零,那么你可能希望将数值标准化为255,而不是整个数值范围
公式将变成:
currentValue/(集合的最大值)请注意,如果您想要越来越亮,亮度不是线性的,因此从值到颜色的直接映射将不会产生好的结果
“颜色”类有一种使颜色更亮的方法。请看一看。这些答案中的大多数都讨论了线性实现,Artelius的答案似乎是最好的。但最好的公式取决于您试图实现的内容和值的分布。如果不知道,很难给出一个理想答案
但是绝对
r(x) = floor(((11.5553 * log(14.4266 * (x + 1.0))) - 30.8419) / 0.9687)
r(x) = floor(255 * log(x + 1) / log(2^31 + 1)