web-dev-qa-db-ja.com

data.tableの名前で列を削除するにはどうすればよいですか?

data.frameの「foo」という名前の列を削除するには、次のようにします。

df <- df[-grep('foo', colnames(df))]

ただし、dfdata.tableオブジェクトに変換されると、単に列を削除する方法はありません。

例:

df <- data.frame(id = 1:100, foo = rnorm(100))
df2 <- df[-grep('foo', colnames(df))] # works
df3 <- data.table(df)
df3[-grep('foo', colnames(df3))] 

しかし、いったんdata.tableオブジェクトに変換されると、これは機能しなくなります。

171
Maiasaura

次のいずれかを実行すると、data.table df3からfoo列が削除されます。

# Method 1 (and preferred as it takes 0.00s even on a 20GB data.table)
df3[,foo:=NULL]

df3[, c("foo","bar"):=NULL]  # remove two columns

myVar = "foo"
df3[, (myVar):=NULL]   # lookup myVar contents

# Method 2a -- A safe idiom for excluding (possibly multiple)
# columns matching a regex
df3[, grep("^foo$", colnames(df3)):=NULL]

# Method 2b -- An alternative to 2a, also "safe" in the sense described below
df3[, which(grepl("^foo$", colnames(df3))):=NULL]

data.tableは、次の構文もサポートしています。

## Method 3 (could then assign to df3, 
df3[, !"foo", with=FALSE]  

ただし、実際に"foo"から列df3を削除したい場合(df3からビュー"foo"を差し引いたものとは対照的に)、代わりに方法1を使用することをお勧めします。

grep()またはgrepl()に依存するメソッドを使用する場合、pattern="^foo$""foo"などの名前の列(つまり、fooをサブストリングとして含む列)も一致させたくない場合は、"fool"ではなく"buffoon"を設定する必要があることに注意してください削除されました。)

安全性の低いオプション、インタラクティブな使用には問題ありません:

次の2つのイディオムも機能します-df3に一致する列が"foo"に含まれる場合-しかし、そうでない場合、おそらく予期しない方法で失敗します。たとえば、それらのいずれかを使用して存在しない列"bar"を検索すると、ゼロ行のdata.tableになります。

結果として、例えば、サブストリング"foo"を含む名前の列を除いたdata.tableを表示する場合など、インタラクティブな使用に最適です。プログラミングの目的(または列のコピーからではなくdf3から実際に列を削除する場合)には、方法1、2a、および2bが本当に最適なオプションです。

# Method 4a:
df3[, -grep("^foo$", colnames(df3)), with=FALSE]

# Method 4b: 
df3[, !grepl("^foo$", colnames(df3)), with=FALSE]
246
Josh O'Brien

これにはsetを使用することもできます。これにより、ループ内の[.data.tableのオーバーヘッドを回避できます。

dt <- data.table( a=letters, b=LETTERS, c=seq(26), d=letters, e=letters )
set( dt, j=c(1L,3L,5L), value=NULL )
> dt[1:5]
   b d
1: A a
2: B b
3: C c
4: D d
5: E e

列名で実行する場合は、which(colnames(dt) %in% c("a","c","e"))jに対して機能するはずです。

29
Ari B. Friedman

私は単にデータフレームのような方法でそれを行います:

DT$col = NULL

速く動作し、私が見る限り、問題は発生しません。

更新:DTが非常に大きい場合、$<-演算子を使用するとオブジェクトがコピーされるため、最適な方法ではありません。だからより良い使用:

DT[, col:=NULL]
16
msp

データテーブルで削除する個々の列が多数あり、すべての列名の入力を避けたい場合の非常に単純なオプション#careadviced

dt <- dt[, -c(1,4,6,17,83,104), with =F]

これにより、代わりに列番号に基づいて列が削除されます。

Data.tableの利点をバイパスするため、明らかに効率的ではありませんが、500,000行未満で作業している場合はうまくいきます

5
SJDS

Dtに列col1col2col3col4col5colnがあるとします。

それらのサブセットを削除するには:

vx <- as.character(bquote(c(col1, col2, col3, coln)))[-1]
DT[, paste0(vx):=NULL]
0
Ricardo Paixao