From tplate at acm.org  Fri Jan 30 18:38:14 2009
From: tplate at acm.org (Tony Plate)
Date: Fri, 30 Jan 2009 10:38:14 -0700
Subject: [Rd] (PR#13487) Segfault when mistakenly calling [.data.frame
In-Reply-To: <157EE908-8A6C-46E4-A9FF-A933A25DEFD9@r-project.org>
References: <20090129153504.D5170282C76F@mail.pubhealth.ku.dk>	<alpine.OSX.1.00.0901292124030.13855@tystie.local>	<c0177e5a0901300730pfe25cb3h3933baa9ef3f26b3@mail.gmail.com>
	<157EE908-8A6C-46E4-A9FF-A933A25DEFD9@r-project.org>
Message-ID: <49833B06.6060508@acm.org>

Simon Urbanek wrote:
>
> On Jan 30, 2009, at 10:30 , Christian Brechb?hler wrote:
>
>> On Thu, Jan 29, 2009 at 4:44 PM, Prof Brian Ripley 
>> <ripley at stats.ox.ac.uk>wrote:
>>
>>> What did your actual application do?  This seems a very strange 
>>> thing to
>>> do, and the segfault is in trying to construct the traceback.
>>>
>>> Only by using do.call on the object (and not even by name) do I get 
>>> this
>>> error.  E.g.
>>>
>>> `[.data.frame`(1:10, 3)
>>>>
>>> Error in NextMethod("[") : object not specified
>>>
>>>> do.call("[.data.frame", list(1:10, 3))
>>>>
>>> Error in NextMethod("[") : object not specified
>>>
>>> are fine.
>>>
>>> Obviously it would be nice to fix this, but I'd like to understand the
>>> actual circumstances: there is more to it than the subject line.
>>
>>
>> Yes, there is more.  For reporting the problem, we tried to pare it 
>> down to
>> a concise, self-contained test case.
>>
>> My boss was debugging an issue in our R code.  We have our own "[...."
>> functions, because stock R drops names when subscripting.
>
> ... if you tell it to do so, yes. If you tell it to not do that, it 
> won't ... ever tried drop=FALSE ?
The common situation I have (which might be the same as the OP's) is 
wanting to get a vector from a data frame, and having the rownames of 
the dataframe become the names on the vector.

With matrix, the behavior I want is the default behavior, e.g.,
 > x <- cbind(a=c(x=1,y=2,z=3),b=4:6)
 > x
  a b
x 1 4
y 2 5
z 3 6
 > x[,1]
x y z
1 2 3

But with a data frame, subscripting returns a vector with no names:
 > xd <- as.data.frame(x)
 > xd[,1]
[1] 1 2 3

One can use drop=FALSE, but then you've still got a data frame, not a 
vector:
 > (xd1 <- xd[,1,drop=FALSE])
  a
x 1
y 2
z 3

The simplest way I know to get a named vector is to use as.matrix on the 
one-column dataframe:
 > as.matrix(xd1)[,1]
x y z
1 2 3
 >
(Which works fine except in the case where xd1 has only one row...)

And BTW, am I missing something, or does the behavior of drop() not 
conform to the description in ?drop:
 > Value:
 >     If 'x' is an object with a 'dim' attribute (e.g., a matrix or
 >     'array'), then 'drop' returns an object like 'x', but with any
 >     extents of length one removed.  Any accompanying 'dimnames'
 >     attribute is adjusted and returned with 'x': if the result is a
 >     vector the 'names' are taken from the 'dimnames' (if any).  If the
 >     result is a length-one vector, the names are taken from the first
 >     dimension with a dimname.

How is this last sentence consistent with the following behavior?
 > dimnames(x[1,1,drop=F])
[[1]]
[1] "x"

[[2]]
[1] "a"

 > drop(x[1,1,drop=F])
[1] 1
 >
 From the description in "Value:" in ?drop, I would have expected above 
result to have the name "x" (the name from the first dimension with a 
dimname).

 > sessionInfo()
R version 2.8.1 (2008-12-22)
i386-pc-mingw32

locale:
LC_COLLATE=English_United States.1252;LC_CTYPE=English_United 
States.1252;LC_MONETARY=English_United 
States.1252;LC_NUMERIC=C;LC_TIME=English_United States.1252

attached base packages:
[1] stats     graphics  grDevices utils     datasets  methods   base    
 >

-- Tony Plate
>
> Cheers,
> S
>
>
>> To bypass our
>> now-suspect functions and get the "real" subscripting method, he used 
>> "get"
>> from package:base.  He was examining a large object, and believing it 
>> was a
>> data frame, chose "[.data.frame".  As it turns out, that object was 
>> not a
>> data frame, and he got an unexpected segfault.  I think it was a matrix.
>> But it doesn't matter -- a vector as in the test case will give the 
>> same.
>>
>> We have since fixed the bug in our replacement subscripting function, 
>> so the
>> issue might not affect us any more.
>>
>> Thanks,
>> /Christian
>>
>>
>>> On Thu, 29 Jan 2009, brechbuehler at gmail.com wrote:
>>>
>>> Full_Name: Christian Brechbuehler
>>>> Version: 2.7.2, 2.8.1
>>>> OS: linux-gnu
>>>>
>>>> If we mistakenly believe the object is a data frame (as we did in a 
>>>> much
>>>> more
>>>> complicated real situation), this happens:
>>>>
>>>>> do.call(get("[.data.frame",pos="package:base"),list(1:10,3))
>>>> Error in NextMethod("[") :
>>>>   no calling generic was found: was a method called directly?
>>>>
>>>>  *** caught segfault ***
>>>> address (nil), cause 'unknown'
>>>>
>>>> Process R:2 segmentation fault (core dumped) at Thu Jan 29 09:26:29 
>>>> 2009
>>>>
>>>> The Error message is appropriate.  But the segmentation fault is
>>>> unexpected.
>>>>
>>>
>>
>>     [[alternative HTML version deleted]]
>>
>> ______________________________________________
>> R-devel at r-project.org mailing list
>> https://stat.ethz.ch/mailman/listinfo/r-devel
>>
>>
>
> ______________________________________________
> R-devel at r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-devel
>



[Rd] (PR#13487) Segfault when mistakenly calling [.data.frame
Tony Plate