All strings in an alpha-numeric range in R

Clash Royale CLAN TAG#URR8PPP
All strings in an alpha-numeric range in R
In R, how can I get a vector of strings given a "range" of strings? (equivalent of x:y, but allowing x and y to be strings of the same length) A couple examples...
"A001":"A003" == c("A001","A002","A003")
"A99":"B02" == c("A99","B00","B01","B02")
update:
I can get "A01":"A10" using
paste0('A',sprintf("%02d",1:10))
[1] "A01" "A02" "A03" "A04" "A05" "A06" "A07" "A08" "A09" "A10"
But I'm not sure how to get from A to B (ie "A99:B02") in a seamless way.
In my particular example the first digit is always alpha (A-Z), and the subsequent digits are always numeric (0-9). And the length of the string would not change. If the strings are of length 3, then the full possible range would be A00:Z99 (need to edit above). After A09 would be A10... After A99 would be B00
– skye
3 hours ago
3 Answers
3
Yep! Here's a working example for ya. The outer function that generates a matrix, but you can always fix with nested list and unlist wrappers
outer
list
unlist
You could do this with a single nums assignment, except you've specified you want two-digit codes, hence the extra paste0 for 1:10
nums
paste0
Note that this won't work for your "wraparound" case where you go from "A99" to "B02", but it'd probably be easier to generate a larger list and then subset it
letts <- c("a", "b", "c")
nums <- c(paste0("0", c(0:9)), 10:99)
sort(unlist(list(outer(letts, nums, paste0))))
Punintended's answer inspired me to figure out a solution that works (including the "wraparound" case where you go from "A99" to "B02")
stringrange = function(x,y)
full =unlist(lapply(LETTERS[which(LETTERS==substr(x,1,1)):which(LETTERS==substr(y,1,1))],
function(x)paste0(x,gettextf(paste0("%02d"),0:99))))
full[which(full==x):which(full==y)]
>stringrange("A98","C03")
[1] "A98" "A99" "B00" "B01" "B02" "B03" "B04" "B05" "B06" "B07" "B08" "B09" "B10" "B11" "B12" "B13" "B14" "B15" "B16" "B17" "B18"
[22] "B19" "B20" "B21" "B22" "B23" "B24" "B25" "B26" "B27" "B28" "B29" "B30" "B31" "B32" "B33" "B34" "B35" "B36" "B37" "B38" "B39"
[43] "B40" "B41" "B42" "B43" "B44" "B45" "B46" "B47" "B48" "B49" "B50" "B51" "B52" "B53" "B54" "B55" "B56" "B57" "B58" "B59" "B60"
[64] "B61" "B62" "B63" "B64" "B65" "B66" "B67" "B68" "B69" "B70" "B71" "B72" "B73" "B74" "B75" "B76" "B77" "B78" "B79" "B80" "B81"
[85] "B82" "B83" "B84" "B85" "B86" "B87" "B88" "B89" "B90" "B91" "B92" "B93" "B94" "B95" "B96" "B97" "B98" "B99" "C00" "C01" "C02"
[106] "C03"
You can do:
str_seq=function(X)
a = toupper(strsplit(X, ':')[[1]])# split while ensuring the letters are uppercase
nums = as.numeric(sub('[A-Z]', '', a))# Obtain the numbers
stopifnot(nums < 100) # If the number for a range is greater than 100 produce an error
a = as.numeric(paste0(setNames(1:26, LETTERS)[sub('\d+', '', a)],sprintf("%02d", nums)))
b = do.call(seq, as.list(c(a, by = if (diff(a) > 0) 1 else -1))) # Ensure you can go forward or backward
b = b[!!b%%100] # Remove A00,B00, etc
paste0(LETTERS[b %/% 100], sprintf("%02d", b %% 100))
str_seq('i89:j23')
[1] "I89" "I90" "I91" "I92" "I93" "I94" "I95" "I96" "I97" "I98" "I99" "J01" "J02" "J03" "J04"
[16] "J05" "J06" "J07" "J08" "J09" "J10" "J11" "J12" "J13" "J14" "J15" "J16" "J17" "J18" "J19"
[31] "J20" "J21" "J22" "J23"
> str_seq('j23:i89')
[1] "J23" "J22" "J21" "J20" "J19" "J18" "J17" "J16" "J15" "J14" "J13" "J12" "J11" "J10" "J09"
[16] "J08" "J07" "J06" "J05" "J04" "J03" "J02" "J01" "I99" "I98" "I97" "I96" "I95" "I94" "I93"
[31] "I92" "I91" "I90" "I89"
By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.
do you have a limit for each range
– akrun
3 hours ago