Reputation: 4362
I have a data frame of this structure which I would like to populate:
V1 V2 V3 V4 V5 V6 V7 V8
1 ID_CODE 0 0 0 0 0 0 0
2 THIS 0 0 0 0 0 0 0
3 ISAROW 0 0 0 0 0 0 0
4 01 0 0 0 0 0 0 0
5 02 0 0 0 0 0 0 0
6 03 0 0 0 0 0 0 0
7 ID_CODE 0 0 0 0 0 0 0
8 THESE 0 0 0 0 0 0 0
9 ARE 0 0 0 0 0 0 0
10 MORE 0 0 0 0 0 0 0
11 ROWS 0 0 0 0 0 0 0
12 01 0 0 0 0 0 0 0
13 02 0 0 0 0 0 0 0
14 03 0 0 0 0 0 0 0
15 ROW 0 0 0 0 0 0 0
And this data frame with the numbers to populate it:
V2_1 V2_2 V2_3 V2_4 V2_5 V2_6 V2_7
1 786 786 786 786 786 786 786
2 786 786 786 786 786 786 786
3 78 78 78 78 78 78 78
4 78 78 78 78 78 78 78
5 78 78 78 78 78 78 78
6 78 78 78 78 78 78 78
These numbers are to go into columns V2:V8 and only in rows in which V1 is a number. The rows in which V1 is a string are to stay as zeroes.
Upvotes: 5
Views: 239
Reputation: 887881
We could create an index based on the presence of numbers in "V1" column of "df1", use that index to subset "df1", multiply that with "df2" after adding "1" (assuming that the dimensions will be the same)
indx <- grep("^\\d+$", df1$V1)
df1[indx,-1] <- df1[indx,-1]+1 *df2
df1
# V1 V2 V3 V4 V5 V6 V7 V8
#1 ID_CODE 0 0 0 0 0 0 0
#2 THIS 0 0 0 0 0 0 0
#3 ISAROW 0 0 0 0 0 0 0
#4 01 786 786 786 786 786 786 786
#5 02 786 786 786 786 786 786 786
#6 03 78 78 78 78 78 78 78
#7 ID_CODE 0 0 0 0 0 0 0
#8 THESE 0 0 0 0 0 0 0
#9 ARE 0 0 0 0 0 0 0
#10 MORE 0 0 0 0 0 0 0
#11 ROWS 0 0 0 0 0 0 0
#12 01 78 78 78 78 78 78 78
#13 02 78 78 78 78 78 78 78
#14 03 78 78 78 78 78 78 78
#15 ROW 0 0 0 0 0 0 0
Upvotes: 4
Reputation: 99371
If df1
is the original and df2
the replacement, then we can use Map
to replace the subset.
## find the rows with only digits in the first column
rows <- grepl("^\\d+$", df1$V1)
## replace the subset with 'df2'
df1[rows, -1] <- Map("[<-", df1[rows, -1], df2)
df1
# V1 V2 V3 V4 V5 V6 V7 V8
# 1 ID_CODE 0 0 0 0 0 0 0
# 2 THIS 0 0 0 0 0 0 0
# 3 ISAROW 0 0 0 0 0 0 0
# 4 01 786 786 786 786 786 786 786
# 5 02 786 786 786 786 786 786 786
# 6 03 78 78 78 78 78 78 78
# 7 ID_CODE 0 0 0 0 0 0 0
# 8 THESE 0 0 0 0 0 0 0
# 9 ARE 0 0 0 0 0 0 0
# 10 MORE 0 0 0 0 0 0 0
# 11 ROWS 0 0 0 0 0 0 0
# 12 01 78 78 78 78 78 78 78
# 13 02 78 78 78 78 78 78 78
# 14 03 78 78 78 78 78 78 78
# 15 ROW 0 0 0 0 0 0 0
Or, another way would be to use replace()
df1[rows, -1] <- Map(function(x, y) replace(x, rows, y), df1[-1], df2)
Upvotes: 4