vlambda博客
学习文章列表

谷歌的R语言编写规范

R是一个高级编程语言主要用于统计计算和图形。R编程风格指南的目标是使我们的R代码更容易阅读、分享和验证。以下R代码规则是在谷歌的整个R合作用户社区下进行设计的。

一、符号和命名(Notation and Naming)

1.1  文件名(File names)

文件名应该以 (.R) 结尾,当然,还要有意义。

正确示例: predict_ad_revenue.R 
错误示例: foo.R

1.2  身份标识(Identifiers)

不要在标识符中使用下划线(_)或连字符(-)。标识符应根据以下约定命名:1、变量名应该包含所有小写字母和用点(.)分隔的单词;2、函数名称有首字母大写字母,没有点(CapWords);3.常量的名称类似函数,首字母一般为 k。

变量名称
正确示例: avg.clicks 
错误示例: avg_Clicks

函数名称
正确示例: CalculateAvgClicks 
错误示例: calculate_avg_clicks , calculateAvgClicks 

制作功能名称动词。 
例外:创建分类对象时,函数名称(构造函数)和类应该匹配(例如,lm)。

二、语法(Syntax)

2.1  每行最大长度(Line Length)

最大行长度为80个字符。

2.2  缩进(Indentation)

当缩进代码, 使用两个空间。绝不使用制表符或混合制表符和空格。例外:括号内发生换行时,使其与括号内的第一个字符对齐。

2.3  间距(Spacing)

当使用所有二进制运算符(如=,+,-,<,等)在两端空格。例外:当符号 = 是函数调用时的传递参数周围不用空格隔开。 
不要在符号“,”前空格隔开,但需要在“,”后添加空格 
正确示例:

tab.prior <- table(df[df$days.from.opt < 0, "campaign.id"])
total <- sum(x[, 1])
total <- sum(x[1, ])

错误示例:

tab.prior <- table(df[df$days.from.opt<0, "campaign.id"])
tab.prior <- table(df[df$days.from.opt < 0,"campaign.id"])
tab.prior<- table(df[df$days.from.opt < 0, "campaign.id"])
tab.prior<-table(df[df$days.from.opt < 0, "campaign.id"])
total <- sum(x[,1])
total <- sum(x[ ,1])

在左括号之前添加一个空格,除了函数的调用的情况 
正确示例:

if (debug)

错误示例:

if(debug)

如果它改善了等号或箭头(<-)的对齐,则额外的间距(即一行中多于一个空格)是可以的。

plot(x = x.coord,
y = data.mat[, MakeColName(metric, ptiles[1], "roiOpt")],
xlab = "dates",
ylab = metric,

main = (paste(metric, " for 3 samples ", sep = "")))

2.4  花括号(Curly Braces)

一个左括号不应该自己一行; 而一个右括号应该总是一行。当一个代码块是一个单独声明时你可以不适用花括号。但是,你必须考虑其他相同的情况,以保持一致。

if (is.null(ylim)) { ylim <- c(0, 0.06) }

或者

if (is.null(ylim)) ylim <- c(0, 0.06)

始终让代码块的主题从新行开始
BAD:

if (is.null(ylim)) ylim <- c(0, 0.06)
if (is.null(ylim)) {ylim <- c(0, 0.06)}

花括号与else 
一个else语句应该总是被花括号包围在同一行。 
Good:

if (condition) {
one or more lines
} else {
one or more lines
}

Bad:

if (condition) {
one or more lines
}
else {
one or more lines
}

2.5  赋值(Assignment)

使用 <-, 而不使用 =, 用于赋值. 
GOOD:

x <- 5

BAD:

x = 5

三、Organization

3.1  总体布局和排序(General Layout and Ordering)

如果每个人都使用相同的一般顺序, 我们能够更快和更容易阅读和理解彼此的脚本。一般开头需包含:

  1. 1.版权声明注释

  2. 2.作者评论

  3. 3.文件描述的评论,包括程序的目的,输入和输出

  4. 4.source() 和 library() 声明

  5. 5.函数定义

  6. 6.已执行的语句

单元测试应该在一个单独的文件名为originalfilename_test.R。

3.2  代码注释(Commenting Guidelines)

简短的注释可以放置在代码之后,用 空格 + # + 空格隔开 ,较长的注释可以单独一行。

# Create histogram of frequency of campaigns by pct budget spent.
hist(df$pct.spent,
breaks = "scott", # method for choosing number of buckets
xlab = "Fraction of budget spent",
ylab = "Frequency (count of campaignids)")

3.3  函数定义和调用(Function Definitions and Calls)

函数定义应该首先列出参数没有默认值, 紧随其后的是那些有默认值的。 
在函数定义和函数调用时,允许多个参数一行,但是换行只允许在参数之间进行。 
GOOD:

PredictCTR <- function(query, property, num.days,
show.plot = TRUE)

BAD:

PredictCTR <- function(query, property, num.days, show.plot =
TRUE)

理想情况下,单元测试应该作为样本函数调用(共享库例程)。

3.4  函数说明(Function Documentation)

在函数定义之下应该包含一个分段注释。这些注释应该包含一句关于函数的描述,一段关于该函数的参数列表的的描述(包括数据类型), 和一个返回值的描述。这些注释需具有足够的描述性的,调用者可以通过阅读注释即可懂得如何调用该函数。

Example

CalculateSampleCovariance <- function(x, y, verbose = TRUE) {
# Computes the sample covariance between two vectors.
#
# Args:
# x: One of two vectors whose sample covariance is to be calculated.
# y: The other vector. x and y must have the same length, greater than one,
# with no missing values.
# verbose: If TRUE, prints sample covariance; if not, not. Default is TRUE.
#
# Returns:
# The sample covariance between x and y.

n <- length(x)
# Error handling
if (n <= 1 || n != length(y)) {
stop("Arguments x and y have different lengths: ",
length(x), " and ", length(y), ".")
}
if (TRUE %in% is.na(x) || TRUE %in% is.na(y)) {
stop(" Arguments x and y must not have missing values.")
}
covariance <- var(x, y)
if (verbose)
cat("Covariance = ", round(covariance, 4), ".\n", sep = "")
return(covariance)
}

四、语言


4.1  连接

使用attach时产生错误的可能性很多,尽量躲开它。

4.2  功能

错误应该使用 stop() 进行提醒

五、最后的话

运用常识,保持一致!

如果您正在编辑代码,请花几分钟查看周围的代码并确定其样式。如果其他人在If子句周围使用空格,你也应该这样做。如果他们的评论周围有小盒子里的星星,你的评论周围也要有小盒子里的星星。

拥有样式指南的关键是拥有一个通用的编码词汇表,这样人们就可以集中精力于您所说的内容,而不是您如何说它。我们在这里介绍全球风格规则,让人们了解词汇。但地方风格也很重要。如果您添加到文件中的代码与周围现有的代码看起来有很大的不同,那么这种不连续性将使读者在阅读时失去节奏。尽量避免这种情况。

好了,写代码的内容就讲到这里;代码本身要有趣得多。享受其中的乐趣!