Dear R-users, I have very recently started learning about object-oriented programming in R. I am far from being an expert in programming, although I do have an elementary C++ background. Please take a look at these lines of code.> some.data = data.frame(V1 = 1:5, V2 = 6:10) ; > p.plot = ggplot(data=some.data,aes(x=V1, y=V2)) ; > class(p.plot) ; > [1] "ggplot"My understanding is that the object p.plot belongs to the "ggplot" class. However, a new class definition like> setClass("AClass", representation(mFirst = "numeric", mSecond = > "ggplot")) ;yields the warning> Warning message: > In .completeClassSlots(ClassDef, where) : > undefined slot classes in definition of "AClass": mSecond(class > "ggplot")The ggplot object is also a list :> is.list(p.plot) > [1] TRUESo, I guess I could identify mSecond as being a list. However, I don't understand why "ggplot" is not considered a valid slot type. I thought setClass() was analogous to the class declaration in C++, but I guess I might be wrong. Would anyone care to provide additional explanations about this? I decided to explore object-oriented programming in R so that I could organize the output from my analysis in a more rigorous fashion and then define custom methods that would yield relevant output. However, I'm starting to wonder if this aspect is not better suited for package builders. R lists are already very powerful and convenient templates. Although it wouldn't be as elegant, I could define functions that would take lists outputted by the different steps of my analysis and do what I want with them. I'm wondering what the merits of both approaches in the context of R would be. If anyone has any thoughts about this, I'd be most glad to read them. Cheers, -- *Luc Villandr?* /Biostatistician McGill University Health Center - Montreal Children's Hospital Research Institute/
Hi. I remember considering these options myself but concluded that for most analyses a strictly procedural approach was satisfactory. Although I may re-run multiple analyses, the data manipulation (and subsequent analysis - the former always more complex than the latter IMHO) is fairly project- and data-specific. As such, quick and specific code always seemed more appropriate than slow (to write) and generic. Obviously that doesn't apply to package creators and maintainers, creating something that is going to re-used in many different projects and can be made generic. That's the heuristic I now use - is this good enough for other people's consumption - if so, create a package and adopt some of the OO approaches seen in the base R packages. Otherwise, stick to bespoke and specific (procedural) functions. I've a small library of helper functions, but these don't use OO usually. They sometimes make assumptions about data passed in, don't have particularly robust error checking, but in general, work well. I suppose it depends on what you're trying to achieve and how much time you've got! Interested in other's thoughts too as clearly there's no "right answer" here. bw Mark 2009/5/27 Luc Villandre <villandl at dms.umontreal.ca>:> Dear R-users, > > I have very recently started learning about object-oriented programming in > R. I am far from being an expert in programming, although I do have an > elementary C++ background. > > Please take a look at these lines of code. >> >> some.data = data.frame(V1 = 1:5, V2 = 6:10) ; >> p.plot = ggplot(data=some.data,aes(x=V1, y=V2)) ; >> class(p.plot) ; >> [1] "ggplot" > > My understanding is that the object p.plot belongs to the "ggplot" class. > However, a new class definition like >> >> setClass("AClass", representation(mFirst = "numeric", mSecond = "ggplot")) >> ; > > yields the warning >> >> Warning message: >> In .completeClassSlots(ClassDef, where) : >> ?undefined slot classes in definition of "AClass": mSecond(class "ggplot") > > The ggplot object is also a list : >> >> is.list(p.plot) >> [1] TRUE > > So, I guess I could identify mSecond as being a list. > > However, I don't understand why "ggplot" is not considered a valid slot > type. I thought setClass() was analogous to the class declaration in C++, > but I guess I might be wrong. Would anyone care to provide additional > explanations about this? > > I decided to explore object-oriented programming in R so that I could > organize the output from my analysis in a more rigorous fashion and then > define custom methods that would yield relevant output. However, I'm > starting to wonder if this aspect is not better suited for package builders. > R lists are already very powerful and convenient templates. Although it > wouldn't be as elegant, I could define functions that would take lists > outputted by the different steps of my analysis and do what I want with > them. I'm wondering what the merits of both approaches in the context of R > would be. If anyone has any thoughts about this, I'd be most glad to read > them. > > Cheers, > -- > *Luc Villandr?* > /Biostatistician > McGill University Health Center - > Montreal Children's Hospital Research Institute/ > > ______________________________________________ > R-help at r-project.org mailing list > https://stat.ethz.ch/mailman/listinfo/r-help > PLEASE do read the posting guide http://www.R-project.org/posting-guide.html > and provide commented, minimal, self-contained, reproducible code. > >-- Dr. Mark Wardle Specialist registrar, Neurology Cardiff, UK
p.plot is an S3 object and you are attempting to define an S4 class so you if you really want to do that then you would need this to let S4 know about the ggplot class: # S4 class with S3 slot setClass("ggplot") # make ggplot visible to S4 setClass("AClass", representation(mFirst = "numeric", mSecond = "ggplot")) a <- new("AClass", mFirst = 1, mSecond = p.plot) Probably you don't want to use S4 at all here but rather define an S3 subclass, "A" of the "ggplot" class and give it an attribute also called "A". # S3 subclass AClass <- function(mFirst, mSecond) { attr(mSecond, "A") <- mFirst class(mSecond) <- c("A", setdiff(class(mSecond), "A")) mSecond } a2 <- AClass(1, p.plot) or alternately represent A as an S3 list holding with the two objects as components: # S3 class but not subclass AClass2 <- function(mfirst, mSecond) { out <- list(mFirst = mFirst, mSecond = mSecond) class(out) <- "A" out } a3 <- AClass2(1, p.plot) Also note that 1. ggplot uses S3 at the user level but uses the "proto" package internally. Depending on what you want to do using proto objects might be preferable. See home page at http://r-proto.googlecode.com 2. R statements do not normally end in a semicolon. On Wed, May 27, 2009 at 12:00 PM, Luc Villandre <villandl at dms.umontreal.ca> wrote:> Dear R-users, > > I have very recently started learning about object-oriented programming in > R. I am far from being an expert in programming, although I do have an > elementary C++ background. > > Please take a look at these lines of code. >> >> some.data = data.frame(V1 = 1:5, V2 = 6:10) ; >> p.plot = ggplot(data=some.data,aes(x=V1, y=V2)) ; >> class(p.plot) ; >> [1] "ggplot" > > My understanding is that the object p.plot belongs to the "ggplot" class. > However, a new class definition like >> >> setClass("AClass", representation(mFirst = "numeric", mSecond = "ggplot")) >> ; > > yields the warning >> >> Warning message: >> In .completeClassSlots(ClassDef, where) : >> ?undefined slot classes in definition of "AClass": mSecond(class "ggplot") > > The ggplot object is also a list : >> >> is.list(p.plot) >> [1] TRUE > > So, I guess I could identify mSecond as being a list. > > However, I don't understand why "ggplot" is not considered a valid slot > type. I thought setClass() was analogous to the class declaration in C++, > but I guess I might be wrong. Would anyone care to provide additional > explanations about this? > > I decided to explore object-oriented programming in R so that I could > organize the output from my analysis in a more rigorous fashion and then > define custom methods that would yield relevant output. However, I'm > starting to wonder if this aspect is not better suited for package builders. > R lists are already very powerful and convenient templates. Although it > wouldn't be as elegant, I could define functions that would take lists > outputted by the different steps of my analysis and do what I want with > them. I'm wondering what the merits of both approaches in the context of R > would be. If anyone has any thoughts about this, I'd be most glad to read > them. > > Cheers, > -- > *Luc Villandr?* > /Biostatistician > McGill University Health Center - > Montreal Children's Hospital Research Institute/ > > ______________________________________________ > R-help at r-project.org mailing list > https://stat.ethz.ch/mailman/listinfo/r-help > PLEASE do read the posting guide http://www.R-project.org/posting-guide.html > and provide commented, minimal, self-contained, reproducible code. >