0

I have multiple xts objects which are all indicators if a stock is above or below a certain median value. These list are structured the following way the size variable is S or B the value variable is H or L and the momentum variable is D or U. This is what part of my three xts objects look like

 `         NESN ROG NOVN ZURN ABBN UBSG LONN 
1989-12-01 "B"  "B" "B"  "S"  "S"  "B"  NA  
1990-01-01 "B"  "B" "B"  "B"  "S"  "B"  NA`  

           NESN ROG NOVN ZURN ABBN UBSG LONN 
1989-12-01 "H"  "L" "L"  "H"  "L"  "L"  NA  
1990-01-01 "H"  "H" "L"  "H"  "L"  "L"  NA

          NESN ROG NOVN ZURN ABBN UBSG LONN 
1989-12-01 "D"  "U" "U"  "D"  "D"  "D"  NA  
1990-01-01 "D"  "U" "D"  "D"  "D"  "U"  NA

Now i want to generate a new list which takes these three lists into account so that I can create a dummy variable equal to 1 when for example a stock is in S, L and D. The result would look something like this:

           NESN ROG NOVN ZURN ABBN UBSG LONN 
1989-12-01 NA  NA   NA   NA   1    NA   NA  
1990-01-01 NA  NA   NA   NA   1    NA   NA

I have tried the following:

SLD_dummy <- ifelse(big_small=="S" & high_low=="L" & up_down=="D",1,NA)

However, I get the following error:

Error in `[.xts`(x, i, which.i = TRUE) : subscript out of bounds

Does anybody know how I can get the desired results? Thanks in advance for your help.

Phil
  • 7,287
  • 3
  • 36
  • 66
Elias K.
  • 513
  • 1
  • 4
  • 12

2 Answers2

2

You could use replace on your xts object:

library(xts)
library(magrittr)
big_small <- as.xts(read.table(text='       NESN ROG NOVN ZURN ABBN UBSG LONN 
                   1989-12-01 "B"  "B" "B"  "S"  "S"  "B"  NA  
                   1990-01-01 "B"  "B" "B"  "B"  "S"  "B"  NA'))

high_low <- as.xts(read.table(text='       NESN ROG NOVN ZURN ABBN UBSG LONN 
1989-12-01 "H"  "L" "L"  "H"  "L"  "L"  NA  
1990-01-01 "H"  "H" "L"  "H"  "L"  "L"  NA'))

up_down <- as.xts(read.table(text='        NESN ROG NOVN ZURN ABBN UBSG LONN 
1989-12-01 "D"  "U" "U"  "D"  "D"  "D"  NA  
1990-01-01 "D"  "U" "D"  "D"  "D"  "U"  NA'))

m <- big_small=="S" & high_low=="L" & up_down=="D"
replace(m, m==T, 1) %>% replace(., m==F, NA)
#>            NESN ROG NOVN ZURN ABBN UBSG LONN
#> 1989-12-01   NA  NA   NA   NA    1   NA   NA
#> 1990-01-01   NA  NA   NA   NA    1   NA   NA

Created on 2021-05-22 by the reprex package (v2.0.0)

(or do m[m==TRUE] <- 1; m[m==FALSE] <- NA)

user12728748
  • 8,106
  • 2
  • 9
  • 14
  • Thank you this is exactly what I was looking for I didn't know that you could combine xts objects with an & – Elias K. May 22 '21 at 13:12
1

We could also do this with Map/Reduce in base R (used R 4.1.0)

library(xts)
Map(`==`, list(big_small, high_low, up_down), c('S', 'L', 'D')) |> 
    {\(x) Reduce(`&`, x)}() |> 
    {\(x) NA^(!x)}()

-output

#          NESN ROG NOVN ZURN ABBN UBSG LONN
#1989-12-01   NA  NA   NA   NA    1   NA   NA
#1990-01-01   NA  NA   NA   NA    1   NA   NA

data

big_small <- structure(c("B", "B", "B", "B", "B", "B", "S", "B", "S", "S", 
"B", "B", NA, NA), .Dim = c(2L, 7L), .Dimnames = list(NULL, c("NESN", 
"ROG", "NOVN", "ZURN", "ABBN", "UBSG", "LONN")), index = structure(c(628491600, 
631170000), tzone = "", tclass = c("POSIXct", "POSIXt")), class = c("xts", 
"zoo"))

high_low <- structure(c("H", "H", "L", "H", "L", "L", "H", "H", "L", "L", 
"L", "L", NA, NA), .Dim = c(2L, 7L), .Dimnames = list(NULL, c("NESN", 
"ROG", "NOVN", "ZURN", "ABBN", "UBSG", "LONN")), index = structure(c(628491600, 
631170000), tzone = "", tclass = c("POSIXct", "POSIXt")), class = c("xts", 
"zoo"))

up_down <- structure(c("D", "D", "U", "U", "U", "D", "D", "D", "D", "D", 
"D", "U", NA, NA), .Dim = c(2L, 7L), .Dimnames = list(NULL, c("NESN", 
"ROG", "NOVN", "ZURN", "ABBN", "UBSG", "LONN")), index = structure(c(628491600, 
631170000), tzone = "", tclass = c("POSIXct", "POSIXt")), class = c("xts", 
"zoo"))
akrun
  • 874,273
  • 37
  • 540
  • 662