简短的问题,如果我有一个字符串,我如何测试该字符串是否是R
中的有效颜色表示?
我尝试了两件事,首先使用函数col2rgb()
来测试它是否是一种颜色:
isColor <- function(x)
{
res <- try(col2rgb(x),silent=TRUE)
return(!"try-error"%in%class(res))
}
> isColor("white")
[1] TRUE
> isColor("#000000")
[1] TRUE
> isColor("foo")
[1] FALSE
工作,但看起来不是很漂亮,也没有矢量化。第二件事是检查字符串是在colors()
向量还是#
后跟一个长度为4到6的十六进制数字:
isColor2 <- function(x)
{
return(x%in%colors() | grepl("^#(\\d|[a-f]){6,8}$",x,ignore.case=TRUE))
}
> isColor2("white")
[1] TRUE
> isColor2("#000000")
[1] TRUE
> isColor2("foo")
[1] FALSE
哪个有效但我不确定它有多稳定。但似乎应该有一个内置函数来进行检查?
答案 0 :(得分:17)
你的第一个想法(使用col2rgb()
来测试颜色名称的有效性)对我来说似乎很好,只需要进行矢量化。至于它是否漂亮......很多/大多数R功能都不是特别漂亮“引擎盖”,这是创建一个功能的主要原因!从用户隐藏所有那些丑陋的内部。
在下面定义areColors()
之后,使用它很容易,因为:
areColors <- function(x) {
sapply(x, function(X) {
tryCatch(is.matrix(col2rgb(X)),
error = function(e) FALSE)
})
}
areColors(c(NA, "black", "blackk", "1", "#00", "#000000"))
# <NA> black blackk 1 #00 #000000
# TRUE TRUE FALSE TRUE FALSE TRUE
答案 1 :(得分:5)
?par
详细说明了在R中指定颜色的方法。任何有效颜色的解决方案都必须考虑:
colors()
"#RRGGBBAA
形式的十六进制表示形式,指定红色,绿色,蓝色和alpha通道。 Alpha通道用于透明,并非所有设备都支持,因此虽然使用8个十六进制值以这种方式指定颜色是有效的,但它可能在特定设备上无效。NA
是有效的&#34;颜色&#34;。它意味着透明,但就R而言,它是一种有效的颜色表示。"transparent"
也有效,但不在colors()
,因此也需要处理 1
是一种有效的颜色表示,因为它是由palette()
> palette()
[1] "black" "red" "green3" "blue" "cyan" "magenta" "yellow"
[8] "gray"
因此,您需要应对1:8
。为什么这很重要,?par
告诉我们将这些颜色的索引表示为字符也是有效的,因此您需要将"1"
捕获为有效的颜色表示。但是(正如@hadley在评论中所指出的那样)默认调色板的只是。用户可以使用另一个调色板,在这种情况下,您必须考虑到您的R版本允许的最大长度的矢量元素的字符索引。
一旦你处理了所有这些,你就应该好好去; - )
据我所知,没有用户可见的功能可以做到这一点。所有这些都埋在C代码中进行绘图;很快你就会在.Internal(....)
土地上结束并且有龙!
[迂腐#000000
在R中不是名 。
唯一的颜色名称 R知道的是colors()
返回的颜色。是的,#000000
是R理解的颜色表示之一,但您明确询问了名称,而最终列表或解决方案是x %in% colors()
,就像您在第二个示例中所做的那样。
这和它一样稳定。当您使用类似col = "goldenrod"
的颜色时,内部R会使用&#34;适当的&#34;表示您正在绘制的任何设备的颜色。 color()
返回R可以执行此操作的颜色名称列表。如果它不在colors()
中,那么它就不是一个颜色名称。