0

I get monthly price value for the two assets below from Yahoo:

if(!require("tseries") | !require(its) ) { install.packages(c("tseries", 'its'));  require("tseries"); require(its) } 
startDate <- as.Date("2000-01-01", format="%Y-%m-%d")
MSFT.prices = get.hist.quote(instrument="msft", start= startDate,
                               quote="AdjClose", provider="yahoo", origin="1970-01-01",
                               compression="m", retclass="its")
SP500.prices = get.hist.quote(instrument="^gspc", start=startDate,
                                quote="AdjClose", provider="yahoo", origin="1970-01-01",
                                compression="m", retclass="its")

I want to put these two into a single data frame with specified columnames (Pandas allows this now - a bit ironic since they take the data.frame concept from R). As below, I assign the two time series with names:

MSFTSP500.prices <- data.frame(msft = MSFT.prices, sp500= SP500.prices )

However, this does not preserve the column names [msft, snp500] I have appointed. I need to define column names in a separate line of code:

colnames(MSFTSP500.prices) <- c("msft", "sp500")

I tried to put colnames and col.names inside the data.frame() call but it doesn't work. How can I define column names while creating the data frame?

I found ?data.frame very unhelpful...

aynber
  • 22,380
  • 8
  • 50
  • 63
Zhubarb
  • 11,432
  • 18
  • 75
  • 114

2 Answers2

2

The code fails with an error message indicating no availability of as.its. So I added the missing code (which appears to have been successful after two failed attempts.) Once you issue the missing require() call you can use str to see what sort of object get.hist.quote actually returns. It is neither a dataframe nor a zoo object, although it resembles a zoo-object in many ways:

> str(SP500.prices)
Formal class 'its' [package "its"] with 2 slots
  ..@ .Data: num [1:180, 1] 1394 1366 1499 1452 1421 ...
  .. ..- attr(*, "dimnames")=List of 2
  .. .. ..$ : chr [1:180] "2000-01-02" "2000-01-31" "2000-02-29" "2000-04-02" ...
  .. .. ..$ : chr "AdjClose"
  ..@ dates: POSIXct[1:180], format: "2000-01-02 16:00:00" "2000-01-31 16:00:00" ...

If you run cbind on those two objects you get a regular matrix with dimnames:

> str(cbind(SP500.prices, MSFT.prices)  )
 num [1:180, 1:2] 1394 1366 1499 1452 1421 ...
 - attr(*, "dimnames")=List of 2
  ..$ : chr [1:180] "2000-01-02" "2000-01-31" "2000-02-29" "2000-04-02" ...
  ..$ : chr [1:2] "AdjClose" "AdjClose"

You will still need to change the column names since there does not seem to be a cbind.its that lets you assign column-names. I would caution about using the data.frame method, since the object is might get confusing in its behavior:

> str( MSFTSP500.prices )
'data.frame':   180 obs. of  2 variables:
 $ AdjClose  :Formal class 'AsIs', 'its' [package ""] with 1 slot
  .. ..@ .S3Class: chr  "AsIs" "its"
 $ AdjClose.1:Formal class 'AsIs', 'its' [package ""] with 1 slot
  .. ..@ .S3Class: chr  "AsIs" "its"

The columns are still S4 objects. I suppose that might be useful if you were going to pass them to other its-methods but could be confusing otherwise. This might be what you were shooting for:

> MSFTSP500.prices <- data.frame(msft = as.vector(MSFT.prices), 
                                 sp500= as.vector(SP500.prices) ,
                           row.names= as.character(MSFT.prices@dates) ) 
> str( MSFTSP500.prices )
'data.frame':   180 obs. of  2 variables:
 $ msft : num  35.1 32 38.1 25 22.4 ...
 $ sp500: num  1394 1366 1499 1452 1421 ...
> head(rownames(MSFTSP500.prices))
[1] "2000-01-02 16:00:00" "2000-01-31 16:00:00" "2000-02-29 16:00:00"
[4] "2000-04-02 17:00:00" "2000-04-30 17:00:00" "2000-05-31 17:00:00"
IRTFM
  • 258,963
  • 21
  • 364
  • 487
1

MSFT.prices is a zoo object, which seems to be a data-frame-alike, with its own column name which gets transferred to the object. Confer

tmp <- data.frame(a=1:10)
b <- data.frame(lost=tmp)

which loses the second column name.

If you do

MSFTSP500.prices <- data.frame(msft = as.vector(MSFT.prices), 
     sp500=as.vector(SP500.prices))

then you will get the colnames you want (though you won't get zoo-specific behaviours). Not sure why you object to renaming columns in a second command, though.

  • I think the constructor should cater for initialising the column names. You're right if I do `as.numeric` or `as.vector` I keep the column names, but then lose the row.names, i.e. the index. – Zhubarb Dec 29 '14 at 16:00
  • @Zhubarb: I don't think that the authors of 'tseries' wanted you to use `data.frame`-methods on their data-objects. Internally the `.Data` core is an R-matrix. – IRTFM Dec 29 '14 at 16:32