30

<-R では、およびを介した代入が可能です=

両方の代入演算子には微妙な違いがありますが、 は値を引数にマッピングする演算子としても使用されるため、 はあいまいなステートメントにつながる可能性があるため<-、 よりも優れた選択である幅広いコンセンサスがあるようです。次に例を示します。==

> system.time(x <- rnorm(10))
   user  system elapsed 
      0       0       0 
> system.time(x = rnorm(10))
Error in system.time(x = rnorm(10)) : unused argument(s) (x = rnorm(10))

実際、Google スタイル コードでは、代入の使用は許可されていません (逆の見方については、この回答=へのコメントを参照してください)。

<-また、代入演算子としてもほぼ独占的に使用しています。ただし、前の文のほとんどがこの質問の理由です。私のコードで代入演算子として機能する場合=、それは常に偶発的であり、それが問題を引き起こす場合、これらは通常見つけにくいです。

割り当てをオフにして、割り当てに使用される=たびにRにエラーをスローさせる方法があるかどうかを知りたい=です。

=アタッチされた名前空間には、割り当てに使用し、壊れてはならないコードが存在する可能性があるため、最適には、この動作はグローバル環境のコードに対してのみ発生します。

(この質問は、ジョナサン・ネルソンとの議論に触発されました)

4

4 に答える 4

37

以下が候補です。

`=` <- function(...) stop("Assignment by = disabled, use <- instead")
# seems to work
a = 1
Error in a = 1 : Assignment by = disabled, use <- instead
# appears not to break named arguments
sum(1:2,na.rm=TRUE)
[1] 3
于 2012-09-13T23:40:03.600 に答える
9

よくわかりませんが、の割り当てを上書きする=だけで十分かもしれません。結局のところ、`=`他の名前とほぼ同じです。

> `=` <- function() { }
> a = 3
Error in a = 3 : unused argument(s) (a, 3)
> a <- 3
> data.frame(a = 3)
  a
1 3

したがって、=for 代入を使用するとエラーが発生しますが、引数に名前を付けるために使用すると有効なままです。問題の行が実際に実行されない限り、関数での使用は見過ごされる可能性があります。

于 2012-09-13T23:40:15.687 に答える
7

パッケージ (CRAN) にはそのためのスタイル チェックがあるため、コードがファイル内にあると仮定すると、それに対して lint を実行すると、割り当てlintのある行番号について警告が表示されます。=

以下に基本的な例を示します。

temp <- tempfile()
write("foo = function(...) {
          good <- 0
          bad = 1
          sum(..., na.rm = TRUE)
       }", file = temp)

library(lint) 
lint(file = temp, style = list(styles.assignment.noeq))
# Lint checking: C:\Users\flodel\AppData\Local\Temp\RtmpwF3pZ6\file19ac3b66b81
# Lint: Equal sign assignemnts: found on lines 1, 3

lintパッケージには、興味深いと思われるいくつかのテストが含まれています。

  • 権利の割り当てに対して警告します
  • 周りのスペースをお勧めします=
  • コンマの後にスペースを推奨
  • 中置記号間のスペースを推奨 (別名二項演算子)
  • タブに対して警告します
  • 最大線幅に対して警告する可能性
  • 関数呼び出し内の代入に対して警告します

定義済みのスタイル チェックをオンまたはオフにすることができ、独自のスタイル チェックを作成できます。ただし、パッケージはまだ初期段階にあります。いくつかのバグ (https://github.com/halpo/lint) があり、ドキュメントを理解するのは少し難しいです。著者は応答性が高く、ゆっくりと改善を行っています。

于 2012-09-14T03:56:39.747 に答える
3

既存のコードを壊したくない場合は、このようなもの(エラーではなく警告を出力する)が機能する可能性があります-警告を与えてから、parent.frame使用に割り当てます<-(再帰を回避するため)

`=` <- function(...){
        .what <- as.list(match.call())
        .call <-  sprintf('%s <- %s', deparse(.what[[2]]),  deparse(.what[[3]]))
        mess <- 'Use <- instead of = for assigment '
        if(getOption('warn_assign', default = T)) {
        stop (mess) } else {
        warning(mess)
        eval(parse(text =.call), envir = parent.frame())  
          }
        }

を設定するとoptions(warn_assign = F)=警告と割り当てが行われます。それ以外のものはエラーをスローし、割り当てません。

使用例

# with no option set
z = 1
## Error in z = 1 : Use <- instead of = for assigment 
options(warn_assign = T)
z = 1
## Error in z = 1 : Use <- instead of = for assigment 
 options(warn_assign = F)
 z = 1
## Warning message:
##  In z = 1 : Use <- instead of = for assigment 

より良いオプション

formatRorlintとコードのフォーマットはより良いアプローチだと思います。

于 2012-09-14T05:43:44.060 に答える