Code:

*! version 1.0.6 07oct2024 version 16.0 clear all loc RS real scalar loc SS string scalar loc SM string matrix mata: mata set matastrict on `SM' ustrregextf(`SM' s1, `SS' re, `SS' t,| `RS' noc) { `RS' i, j `SS' g, s noc = noc != . ? noc : 0 s = st_tempname() for(i = 1; i <= rows(s1); i++) { for(j = 1; j <= cols(s1); j++) { (void) ustrregexm(s1[i,j], re, noc) if ((g=ustrregexs(0)) != "") { stata(`"mata: st_strscalar(""' + s + `"", "' + t + `"(""' + g + `""))"') s1[i,j] = usubinstr(s1[i,j], g, st_strscalar(s), 1) } } } return(s1) } `SM' ustrregexta(`SM' s1, `SS' re, `SS' t,| `RS' noc) { `RS' i, j `SS' g, g_flag, s noc = noc != . ? noc : 0 s = st_tempname() for(i = 1; i <= rows(s1); i++) { for(j = 1; j <= cols(s1); j++) { while(1) { (void) ustrregexm(s1[i,j], re, noc) if ((g=ustrregexs(0)) != "" & g != g_flag) { stata(`"mata: st_strscalar(""' + s + `"", "' + t + `"(""' + g + `""))"') s1[i,j] = usubinstr(s1[i,j], g, (g_flag=st_strscalar(s)), 1) } else break } } } return(s1) } end version 18.0: lmbuild llanguagetools.mlib, replace size(4)

Code:

mata: st_sview((X=""), ., "varname"); ustrregexta(X, ",\s*[a-z]", "ustrupper");

Code:

mata: st_sstore(., "varname", ustrregexta(st_sdata(., "varname"), ",\s*[a-z]", "ustrupper"))

For an N dimensional vector, I want to form an N X N matrix of indicators showing whether two elements of the vector share the same value. E.g.,

Code:

. mat v = (1,2,4,4) . mat list v v[1,4] c1 c2 c3 c4 r1 1 2 4 4 . mat R = (1,0,0,0 \ 0, 1 , 0, 0 \ 0 , 0, 1, 1 \ 0, 0, 1, 1) . matlist R | c1 c2 c3 c4 -------------+------------------------------------------- r1 | 1 r2 | 0 1 r3 | 0 0 1 r4 | 0 0 1 1

I managed to do this in Mata using a double loop.

I am wondering whether there is some vectorised clever way to do this, which results in faster computation that the double loop I am doing below?

The two versions of the doble loop follow. One is just a direct double loop from 1 to N; in the second version I tried to be clever and to cut down the loop in half, as the R matrix is symmetric. However this does not seem to save much execution time.

Code:

sysuse auto expand 400 replace rep = 6 if missing(rep) putmata N = rep timer on 1 mata: obs = rows(N) R = I(obs) for (i=1; i<=obs; i++) { for (j=1; j<i; j++) { R[i,j]=N[i]==N[j] } } R = R + R' - I(obs) end timer off 1 timer on 2 mata: obs = rows(N) Rcorrect = I(obs) for (i=1; i<=obs; i++) { for (j=1; j<=obs; j++) { Rcorrect[i,j] = N[i]==N[j] } } end timer off 2 mata: mreldif(Rcorrect, R) timer list

Code:

. sysuse auto (1978 automobile data) . . . keep in 1/13 (61 observations deleted) . . replace rep = 6 if missing(rep) (2 real changes made) . . putmata N = rep (1 vector posted) . . . timer on 2 . mata: ------------------------------------------------- mata (type end to exit) ------------------------------------------------------------------------------------------------------ : obs = rows(N) : Rcorrect = I(obs) : for (i=1; i<=obs; i++) { > for (j=1; j<=obs; j++) { > Rcorrect[i,j] = N[i]==N[j] > } > } : N 1 +-----+ 1 | 3 | 2 | 3 | 3 | 6 | 4 | 3 | 5 | 4 | 6 | 3 | 7 | 6 | 8 | 3 | 9 | 3 | 10 | 3 | 11 | 3 | 12 | 2 | 13 | 3 | +-----+ : Rcorrect [symmetric] 1 2 3 4 5 6 7 8 9 10 11 12 13 +------------------------------------------------------------------+ 1 | 1 | 2 | 1 1 | 3 | 0 0 1 | 4 | 1 1 0 1 | 5 | 0 0 0 0 1 | 6 | 1 1 0 1 0 1 | 7 | 0 0 1 0 0 0 1 | 8 | 1 1 0 1 0 1 0 1 | 9 | 1 1 0 1 0 1 0 1 1 | 10 | 1 1 0 1 0 1 0 1 1 1 | 11 | 1 1 0 1 0 1 0 1 1 1 1 | 12 | 0 0 0 0 0 0 0 0 0 0 0 1 | 13 | 1 1 0 1 0 1 0 1 1 1 1 0 1 | +------------------------------------------------------------------+ : end ------------------

]]>

I would like to form a block diagonal matrix which has square blocks of 1s on the diagonal, and the dimensions of these blocks are given in a Stata-vector. E.g.,

Code:

. sysuse auto, clear (1978 automobile data) . levelsof rep, matcell(Dimensions) 1 2 3 4 5 . mat list Dimensions Dimensions[5,1] c1 r1 2 r2 8 r3 30 r4 18 r5 11 . return list scalars: r(N) = 69 r(r) = 5 macros: r(levels) : "1 2 3 4 5"

If it is of any help, this is how I do this in Stata:

Code:

. mat Blocks = J(r(N),r(N),0) . scalar J = 1 . forvalues l = 1/`r(r)' { 2. mat Blocks[J,J] = J(Dimensions[`l',1], Dimensions[`l',1], 1) 3. scalar J = J + Dimensions[`l',1] 4. }

I have a lot of Excel documents with many sheets within each. However, for some sheets, I need to delete specific elements that are no longer needed (at least for now). I would rather not delete them manually in Excel.

I have previously used mata to manipulate the Excel files, but I can't figure out how to delete specific columns, rows, or cells.

My approach for manipulating in terms of e.g. column width and cell merging is e.g.:

Code:

mata: b = xl() mata: b.load_book("my file") mata: b.set_sheet("sheet") mata: b.set_column_width(1,5,15)

(Note: I apply 'mata:' before each command as I apply these within a loop).

Thank you.

Best,

Lau]]>