# 幅 3, 2, 2, 3 である固定長データを読み込む
--- sample.txt ここから ---
0010918111
0021002222
00311233 3
0044 344
--- sample.txt ここまで ---
# 変数名,変数の型,幅の長さが書かれているテキストファイルを用意する
--- mylab.txt ここから ---
VAR1 numeric 3
VAR2 factor 2
VAR3 factor 2
VAR4 numeric 3
--- mylab.txt ここまで ---
# R上で以下のようにコマンドする
> mylab <- read.table("mylab.txt", colClasses=c("character", "character", "numeric"))
> mylab
V1 V2 V3
1 VAR1 numeric 3
2 VAR2 factor 2
3 VAR3 factor 2
4 VAR4 numeric 3
> #この方法だと元のデータにいくつの半角スペースが含まれているか確認できないので不都合(2つの半角スペースだけならよいが・・・)
> dat2 <- read.fwf("sample.txt", widths=mylab$V3,
+ col.names=mylab$V1, colClasses=mylab$V2, na.strings=c(" "))
> dat2
VAR1 VAR2 VAR3 VAR4
1 1 09 18 111
2 2 10 02 222
3 3 11 23 33
4 4 4344
> #空白がそのまま読み込まれては不都合(NAにしたい)
> dat2 <- read.fwf("sample.txt", widths=mylab$V3,
+ col.names=mylab$V1, colClasses=mylab$V2)
> dat2
VAR1 VAR2 VAR3 VAR4
1 1 09 18 111
2 2 10 02 222
3 3 11 23 33
4 4 4 344
> #これがベターだが,変数の再定義が必要。でもどうやって?
> dat2 <- read.fwf("sample.txt", widths=mylab$V3,
+ col.names=mylab$V1, colClasses="numeric")
> dat2
VAR1 VAR2 VAR3 VAR4
1 1 9 18 111
2 2 10 2 222
3 3 11 23 33
4 4 4 NA 344
No.13741 Re: 幅固定欄ファイルの読み込みと変数定義 【青木繁伸】 2010/11/07(Sun) 22:45
dat2 <- read.fwf("sample.txt", widths=mylab$V3,のあと,mylab$V2 が factor の変数のみ dat2 のその変数に factor( ) を作用させるのですか?
col.names=mylab$V1, colClasses="numeric")
factor にすべき変数が dat2 の何列目かを表すベクトルを用意すれば,for (i in c(2, 3)) dat2[,i] <- factor(dat2[,i])のようにすればよいと思います。そのようなベクトルも mylab から作れます。for (i in (1:nrow(mylab))[mylab$V2=="factor"]) {あるいは,
dat2[,i] <- factor(dat2[,i])
}for (i in 1:nrow(mylab)) {も同じですね。
if (mylab$V2[i] == "factor") {
dat2[,i] <- factor(dat2[,i])
}
}
また,さらに面倒くさいですけど,for (i in 1:nrow(mylab)) {実行結果は
if (mylab$V2[i] == "factor") {
vname <- mylab$V1[i]
eval(parse(text=sprintf("dat2$%s <- factor(dat2$%s)", vname, vname)))
}
}> mylab <- read.table("mylab.txt", colClasses=c("character", "character", "numeric"))ま たは,na.strings はベクトルでよいので,na.strings=sapply(1:10, function(i) paste(rep(" ", i), collapse="")) などとしておくと 10 桁までの空白が NA にできるので都合がよいかもしれません。
> dat2 <- read.fwf("sample.txt", widths=mylab$V3,
+ col.names=mylab$V1, colClasses="numeric")
> sapply(dat2, class)
VAR1 VAR2 VAR3 VAR4
"numeric" "numeric" "numeric" "numeric"
> for (i in 1:nrow(mylab)) {
+ if (mylab$V2[i] == "factor") {
+ vname <- mylab$V1[i]
+ eval(parse(text=sprintf("dat2$%s <- factor(dat2$%s)", vname, vname)))
+ }
+ }
> dat2
VAR1 VAR2 VAR3 VAR4
1 1 9 18 111
2 2 10 2 222
3 3 11 23 33
4 4 4 <NA> 344
> sapply(dat2, class)
VAR1 VAR2 VAR3 VAR4
"numeric" "factor" "factor" "numeric"
No.13742 Re: 幅固定欄ファイルの読み込みと変数定義 【波音】 2010/11/08(Mon) 22:41
早速の回答ありがとうございます。
やはり基本的にはfor構文を用いて繰り返し処理をしていくの がベターのようですね。if文を用いたやり方のほうが馴染み深いものですが,(1:nrow(mylab))[mylab$V2=="factor"]と いう表現(書き方は)初めて知ったのでとても参考になりました。
na.strings=sapply(1:10, function(i) paste(rep(" ", i), collapse=""))で複数個の空白が格納されているベクトルを用意する方法も良いですが,forによる繰り返し処理であってもそれほど時間を要す るわけでもないので,とりあえず作業工程で都合のよい方をその都度使ってみようと思います。
● 「統計学関連なんでもあり」の過去ログ--- 044 の目次へジャンプ
● 「統計学関連なんでもあり」の目次へジャンプ
● 直前のページへ戻る