Bookmark and Share

Notice: On April 23, 2014, Statalist moved from an email list to a forum, based at statalist.org.


[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

RE: st: saving space while recoding


From   "Martin Weiss" <[email protected]>
To   <[email protected]>
Subject   RE: st: saving space while recoding
Date   Mon, 26 Jul 2010 08:29:42 +0200

<>

The -inrange()- function may also be helpful for Sarah. See Nick`s SJ
article at http://www.stata-journal.com/sjpdf.html?articlenum=dm0026



HTH
Martin


-----Original Message-----
From: [email protected]
[mailto:[email protected]] On Behalf Of Eric Booth
Sent: Montag, 26. Juli 2010 05:14
To: <[email protected]>
Subject: Re: st: saving space while recoding

<>


You were close.  The "22<=newvar2<=25" part should read "(22<=newvar2 &
newvar2<=25)".  
To make my previous example 1 work with your new list, which has 3 items per
loop rather than 2, take a look at these changes:

**********************!
//EXAMPLE 1 redux //
sysuse auto, clear
local list  mpg 22 26 rep78 3 4 turn 17 20  weight 2240 3600  length 170 204
**
token `"`list'"'
di `"`list'"'
	while "`1'" != "" {
	  di "recode `1' for range defined by `2' and `3' "
	  g i`1' = cond((`2'<=`1' & `1'<=`3'), 0, cond(missing(`1'), .,
(cond(`1'<`2', -1, 1))))
	  mac shift 3    //this part increases the macro `1' by 2 to `3'
	}
sort mpg
order *mpg
**********************!

~ Eric
__
Eric A. Booth
Public Policy Research Institute
Texas A&M University
[email protected]
Office: +979.845.6754

On Jul 25, 2010, at 9:14 PM, sarah plank wrote:

> Now I have a second list given me where there are some ranges instead
> of single cutoff points, so for list  "newvar2 22 25  newvar3  33.5
> 26  newvar9  55.5  100 "  I need to recode values less than first
> range point to -1, values between range to zero, and points above the
> second range point to 1.  With the replace command, I can do it:
> generate var = -1 if newvar2<=22
> replace var = 0 if newvar2>=22 & newvar2<=25
> replace var = 1 if newvar2>= 25 & newvar2!=.
> 
> and I tried to paste this into the code I got earlier but it doesnt work.
> gen var = cond(22<=newvar2<=25, 0, cond(missing(newvar2), .,
> (cond(newvar2<22, -1, 1))
> 
> This gives me all zeros !  How can I edit this code to work with my
> new list and make this work in a loop to save space ?
> 
> 
> 
> 
> 
> On Sat, Jul 24, 2010 at 5:58 PM, sarah plank <[email protected]>
wrote:
>> Oh my gosh, how great!   I copied and pasted my list into the first
>> example and it is working, I am running it now but I hope it doesnot
>> break because I dont understand it enough to make changes.  Thanks.
>> 
>> On Sat, Jul 24, 2010 at 4:35 PM, Eric Booth <[email protected]> wrote:
>>> <>
>>> 
>>> 
>>> There are a couple of possibilities here.   First, you can get rid of
the 3 -replace- statements with one -recode- statement that does the same
thing, e.g.,
>>> 
>>> ******!
>>> recode polyclornew (min/44 = -1)  (45=0)  (46/max = 1) (.=.)
>>> ******!
>>> 
>>> but this doesn't make managing your long list of recode conditions much
easier.  Also,  a warning: note that the -replace- codes in your example
will not recode any values between 44 and 45 (such as 44.5)  nor values
between 45 & 46.  Given that a lot of the values in the list your provided
aren't integers, this might be a concern.
>>> 
>>> In terms of making your code shorter you might consider using the
-cond()- function.  For example,
>>> **********************!
>>> sysuse auto, clear
>>> keep price
>>> qui g i = cond(price==4099, 0, cond(missing(price), ., (cond(price<4099,
-1, 1))))
>>> sort price
>>> **********************!
>>> will recode price around the 4,099 threshold.
>>> A brief explanation of what this code is doing is probably helpful here:
if price is == 4099 it will recode i to 0.   If not, it will evaluate the
last "cond(missing(price), ., (cond(price<4099, -1, 1)) " part.    Within
this last part it will recode i to -1 if price is less than 4099 and i to 1
if price is greater than or equal to 4099 (but it has already recoded to 0
if price is equal to 4099, so it will just recode to 1 if price is greater
than 4099 in this case) .  See -help cond- for more.
>>> 
>>> To make this work with a long list of conditions like the ones you have
provided, you could break the list up into macros &/or  use -tokenize- to
loop over the pairs of items in your list.  Here are two examples using the
-auto.dta- again:
>>> 
>>> 
>>> **********************!
>>> //EXAMPLE 1//
>>>    /*
>>> This example uses the list if it is formatted as you presented it in
your posting--it will make the changes to items 1 (mpg) and 2(23) in the
list and then move on the items 3 and 4 in the list and so on to the end
>>>    */
>>> 
>>> sysuse auto, clear
>>> local list  mpg 23  rep78 3 turn 17 weight 2930 length 196
>>> **
>>> token `"`list'"'
>>> di `"`list'"'
>>>        while "`1'" != "" {
>>>         di "recode `1' for value `2'"
>>>          g i`1' = cond(`1'==`2', 0, cond(missing(`1'), ., (cond(`1'<`2',
-1, 1))))
>>>          mac shift 2    //this part increases the macro `1' by 2 to `3'
>>>        }
>>> sort mpg
>>> order *mpg
>>> **********************!
>>> 
>>> Alternatively, if your list were organized down a column in a
spreadsheet or something, you could add -local- and a macname to each pair
of items to be used for the recodes and loop over each condition.
>>> 
>>> **********************!
>>> //EXAMPLE 2//
>>> sysuse auto, clear
>>> 
>>> **items in your list:
>>> local one  mpg 23
>>> local two  rep78 3
>>> local three turn 17
>>> local four weight 2930
>>> local five length 196
>>> 
>>> foreach x in one two three four five {
>>>        token ``x''
>>>        di "``x''"
>>>        di "recode `1' for value `2'"
>>>          g i`1' = cond(`1'==`2', 0, cond(missing(`1'), ., (cond(`1'<`2',
-1, 1))))
>>> }
>>> sort mpg
>>> order *mpg
>>> **********************!
>>> 
>>> ~ Eric
>>> __
>>> Eric A. Booth
>>> Public Policy Research Institute
>>> Texas A&M University
>>> [email protected]
>>> Office: +979.845.6754
>>> 
>>> 
>>> 
>>> 
>>> 
>>> On Jul 24, 2010, at 4:22 PM, sarah plank wrote:
>>> 
>>>> I need to create a recode but save some space in my code.   I have
>>>> lots of recodes where I am given the variable to recode and the cutoff
>>>> point over which to recode the variables.  So, given my list of
>>>> "polyclor 23.4    polyclor2  33.3  pavol 45  genpt  1.11  gnpt  1  on
>>>> 0  offon 0  offon2 1  got5  66  {+ 670 more items}"  I need to recode
>>>> them all by their cutoff in the list, so
>>>> 
>>>> clonevar polyclor2 = polyclornew
>>>> replace polyclornew = -1 if polychlornew<44
>>>> replace polyclornew = 0 if polyclornew==45
>>>> replace polyclornew = 1 if polyclornew>46 & polyclornew!=.
>>>> tab polyclornew
>>>> 
>>>> but this is so exhausting for so many values and so long in the
>>>> do-code.  How can I make this in less space ?
>>>> *
>>>> *   For searches and help try:
>>>> *   http://www.stata.com/help.cgi?search
>>>> *   http://www.stata.com/support/statalist/faq
>>>> *   http://www.ats.ucla.edu/stat/stata/
>>> 


*
*   For searches and help try:
*   http://www.stata.com/help.cgi?search
*   http://www.stata.com/support/statalist/faq
*   http://www.ats.ucla.edu/stat/stata/

*
*   For searches and help try:
*   http://www.stata.com/help.cgi?search
*   http://www.stata.com/support/statalist/faq
*   http://www.ats.ucla.edu/stat/stata/


© Copyright 1996–2018 StataCorp LLC   |   Terms of use   |   Privacy   |   Contact us   |   Site index