[Rd] Basic Question regarding PROTECT

Duncan Murdoch murdoch at stats.uwo.ca
Mon Aug 24 15:39:54 CEST 2009


On 8/24/2009 9:33 AM, Saptarshi Guha wrote:
> Thank you. So the reason I wouldnt need to protect y had I returned to
> R, is because
> had i had done something like
> 
> h<-.Call("boo",a)
> where "boo" contains y=foo()
> 
> the assignment "<-" to h would have a PROTECT somewhere, i.e R's
> assignment is doing the protection for me.

Once the object is assigned to h, then it is stored in the global 
environment, so it is safe from garbage collection without needing to be 
PROTECTed.  It's just in the short time after creation before storage 
where it's at risk.

One general rule in R is that things are in use if they are part of 
something that is in use (and the global environment is always in use). 
  PROTECT is another way to mark something as being in use.  When 
something is in use the garbage collector will leave it alone.

Duncan Murdoch


> Had I not returned to R, I would have to do it myself.
> 
> Yes PROTECT is quite cheap, I had thought it to be costly but 1MM
> PROTECT/UNPROTECT calls, takes <1 second  (on a macbook 2.16ghz)
> 
> Thanks for the explanation.
> Regards
> Saptarshi
> 
> On Mon, Aug 24, 2009 at 9:24 AM, Duncan Murdoch<murdoch at stats.uwo.ca> wrote:
>> On 8/24/2009 9:10 AM, Sapsi wrote:
>>>
>>> Hello
>>> Thank you for the response. So if my call is
>>>
>>> y=foo()
>>> z=malloc ( by memory allocations , do you mean via R_alloc and
>>>  allocVector and malloc or just the former two)
>>
>> Any allocation which is managed by R's memory manager, so that includes the
>> former two, and many other kinds of calls which do allocations, i.e.
>> essentially any call to the R API unless it's documented not to do
>> allocations. In most cases calling PROTECT is quite cheap, so it is worth
>> doing if you're not sure.  (There are exceptions:  because the PROTECT stack
>> is finite, you can overflow it if you PROTECT too much. That could happen in
>> a loop or a deep recursion.)
>>
>>
>>> Other statements
>>>
>>> Then I need  to protect y. And in my case I don't return to R since I
>>>  have embedded it.
>>>
>>> Why is this the case I.e if I perform mem allocs , I need to protect y
>>
>> Because R's memory manager does automatic garbage collection.  If you don't
>> protect y, then the memory manager will not know that it is still in use.
>>  The next time it needs some memory it may decide to free y and re-use that
>> space.
>>
>> Duncan Murdoch
>>
>>
>>> On Aug 24, 2009, at 8:18 AM, Duncan Murdoch <murdoch at stats.uwo.ca>
>>> wrote:r
>>> C
>>>>
>>>> On 8/23/2009 11:52 PM, Saptarshi Guha wrote:
>>>>>
>>>>> Hello,
>>>>> Suppose I have the function
>>>>> SEXP foo(){
>>>>> SEXP s;
>>>>> PROTECT(s=allocVector(...))
>>>>> ....
>>>>> UNPROTECT(1);
>>>>> return(s)
>>>>> }
>>>>> y=foo() // foo is a recusrive call
>>>>> Q: Am i correct in understanding that one does not need to write
>>>>> PROTECT(y=foo()) ?(and a corresponding unprotect  later on)
>>>>> since it is the object that is protected , SEXP is an alias for
>>>>> SEXPREC* and allocVector probably does some memory allocation which
>>>>> does not get freed
>>>>> when foo returns.
>>>>
>>>> Whether y needs protecting depends on what happens between the y =  foo()
>>>> call and the time you return to R.  If nothing happens, i.e.  you just
>>>> return y to R, then you're safe.  If you do any memory  allocations after
>>>> that call before returning to R then y will need  to be protected.
>>>>
>>>> Duncan Murdoch
>>
>>



More information about the R-devel mailing list