Announcement

Collapse
No announcement yet.
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Program to label variables from list of words - How to use fewer single and double quotes

    I am used to make reusable programs, and find myself having issues with how I use the local single quotes and double quotes. After a lot of trial and error with using double quotes around locals, I managed to get the following program to work. But I do not understand why this has to be this way. Sometimes I felt that I just spammed single and double quotes until it worked.

    I think I can see why I need the single quotes when I define the local `names', but why do I have to use `"`names'"' when calling the function? This makes for so many quotes everywhere, and is confusing to both read and understand. Any suggestion to make this program more refined, or maybe help me understand why the quotes work as they do when I define and call the local `names' would be very welcome. I have tried to read https://www.stata.com/manuals13/u18.pdf at "18.3.5 Double quotes" and other forum posts, but I am still confused.

    Code:
    clear all
    sysuse auto
    
    capture program drop label_variables
    program define label_variables
    version 16.1
    args var_list name_list
        ds `var_list'
        local n_words : word count `name_list'
        forvalues i = 1/`n_words' {
            local _var : word `i' of `r(varlist)'
            local _name : word `i' of `name_list'
            label variable `_var' "`_name'"
        }
    end
    
    local names `""Make of Car" "Price of Car" "Mileage of Car""'
    label_variables make-mpg `"`names'"'
    describe make-mpg

  • #2
    The principle that bites most often is that Stata will always strip the outermost quotes each time a local is defined. As it happens I think your code would also have worked with


    Code:
    local names " "Make of Car" "Price of Car" "Mileage of Car" "
    Your program is limited to two arguments, a variable list and a name list (really a label list), although you can get flexibility by using quotation marks. Something like this is a little less awkward and includes a hint about checking for problems:


    Code:
    clear all
    sysuse auto
    
    capture program drop label_variables
    program define label_variables
        version 16.1
        syntax varlist, labels(str asis) 
     
        local n_labels : word count `labels'
        local n_vars : word count `varlist'
        
        if `n_labels' != `n_vars'  exit 498 
        
        forvalues i = 1/`n_labels' {
            local var : word `i' of `varlist'
            local label : word `i' of `labels'
            label variable `var' "`label'"
        }
    end
    
    local labels `""Make of Car" "Price of Car" "Mileage of Car""'
    label_variables make-mpg , labels(`labels')
    describe make-mpg

    Comment


    • #3
      Nick gives excellent advice.

      I would probably use compound double quotes and change

      Code:
      label variable `var' "`label'"
      to

      Code:
      label variable `var' `"`label'"'
      because variable labels might well contain double quotes. This approach bites if variable labels contain left single quotes.


      For the underlying problem, also see elabel (SSC). It implements yet another syntax:

      Code:
      local labels `""Make of Car" "Price of Car" "Mileage of Car""'
      elabel variable (make-mpg) (`labels')
      using parentheses to separate the two [groups/types of] arguments.
      Last edited by daniel klein; 02 Nov 2020, 07:53.

      Comment


      • #4
        Thanks for this Nick, as alway very good help. I find it difficult to declare namespaces in Stata, since it is wildly different to what I am used to. But this way of declaring the labels in an options seems quite elegant, and I will try to remember this way to create programs the next time I make a program. This was very helpful and learnt a lot!

        Originally posted by Nick Cox View Post
        The principle that bites most often is that Stata will always strip the outermost quotes each time a local is defined. As it happens I think your code would also have worked with


        Code:
        local names " "Make of Car" "Price of Car" "Mileage of Car" "
        Your program is limited to two arguments, a variable list and a name list (really a label list), although you can get flexibility by using quotation marks. Something like this is a little less awkward and includes a hint about checking for problems:


        Code:
        clear all
        sysuse auto
        
        capture program drop label_variables
        program define label_variables
        version 16.1
        syntax varlist, labels(str asis)
        
        local n_labels : word count `labels'
        local n_vars : word count `varlist'
        
        if `n_labels' != `n_vars' exit 498
        
        forvalues i = 1/`n_labels' {
        local var : word `i' of `varlist'
        local label : word `i' of `labels'
        label variable `var' "`label'"
        }
        end
        
        local labels `""Make of Car" "Price of Car" "Mileage of Car""'
        label_variables make-mpg , labels(`labels')
        describe make-mpg

        Comment

        Working...
        X