#install.packages("gregmisc") library (gregmisc) # This function takes as input different types of well phrases and returns a list of individual wells that this represents. # e.g. # in_well_phrase = "A1" # in_well_phrase = "A1, B1, D1, C1" # in_well_phrase = "A1:H1" # in_well_phrase = "A1:H1, A2:H2" list_well_names_from_LUT_well_phrase <- function(in_well_phrase) { #If the well phrase is just a single well like A1, validate it is a valid well then return that well. if (nchar(in_well_phrase) == 2) { validate.single.well.input(in_well_phrase) return (in_well_phrase) } # else... continue... # now check if it is a single phrase, or multiple phrases # if A1, A2, B1, B2 or A1:H1, B1:H1 well_phrases = unlist(strsplit(in_well_phrase, ",")) # create an array well_phrases = trim(well_phrases) # remove spaces # now you have a list of wells... or a list of well phrases. if (nchar(well_phrases[1]) == 2) { # then you have a list of wells (e.g. "A1, B1, C1" ) lapply (well_phrases, validate.single.well.input) # will throw error if invalid well form return (well_phrases) } else if (nchar(well_phrases[1]) > 4) { # you have a list of one or more well phrases (e.g. "A1:B1", or "A11:H11" or "A1:F1, A2:F2") # validate list of wells first... output_well_list_from_single_phrase = character(0) output_well_list_from_single_phrase = c(output_well_list_from_single_phrase, lapply(well_phrases, list_well_names_from_single_well_phrase)) output_well_list_from_single_phrase = unlist(output_well_list_from_single_phrase) # now you should have the wells in a particular series # next let's put this into a list of wells. print (paste("output well list: ", output_well_list_from_single_phrase)) return(output_well_list_from_single_phrase) # this returns a list of wells. } print (paste("input well phrase: ", in_well_phrase)) # output_well_list = "A1, B1, C1, D1" # print (paste("output well list: ", output_well_list)) # return(output_well_list) } # function to get list of wells from a single phrase like A1:D1 list_well_names_from_single_well_phrase <- function(single_in_well_phrase) { print (paste("input well phrase: ", single_in_well_phrase)) # all the cols must be the same in one input statement e.g. A1:D1 is fine, but #A1:D3 is not. #Convert well language from A1:D1 to a list of wells, A1, B1, C1, D1 wells_for_series = strsplit(single_in_well_phrase, ":") # create an array of first and last wells_for_series = unlist(wells_for_series) first_well = wells_for_series[1] validate.single.well.input (first_well) first_well_row=substr(first_well,1,1) first_well_col=as.integer(substr(first_well,2,nchar(first_well))) # subst gets what ever is left after the letter (e.g. 1 or 2 digits) # check it is a valid letter+number combination last_well = wells_for_series[2] validate.single.well.input (last_well) # check it is a valid letter+number combination last_well_row=substr(last_well,1,1) last_well_col=as.integer(substr(last_well,2,nchar(last_well))) # get the indices from A-Z for the letters you want first_letter_index = which(LETTERS== first_well_row) last_letter_index = which(LETTERS== last_well_row) numer_of_rows = length(LETTERS[first_letter_index:last_letter_index]) # just a reminder that all the cols must be the same in one input statement e.g. # A1:D1 is fine, but A1:D3 is not. output_well_list_from_single_phrase = data.frame("row" = LETTERS [first_letter_index:last_letter_index], "col" = c(rep(first_well_col, numer_of_rows)) ) # now turn the df into a list of wells output_well_list_from_single_phrase = apply(output_well_list_from_single_phrase, 1, paste, collapse="") output_well_list_from_single_phrase # now you should have the wells in a particular series # next let's put this into a list of wells. print (paste("output well list: ", output_well_list_from_single_phrase)) return(output_well_list_from_single_phrase) } # this function validates each A1 or D1 for example... to check it is a single letter and number...\ validate.single.well.input <- function(x){ match <- grepl("^[A-Ha-h]([0-9]|(1[0-2]))$",x,perl=TRUE) ## as Marek points out, instead of testing the length of the vector ## returned by grep() (which will return the index of the match and integer(0) ## if there are no matches), we can use grepl() if(!match) stop("invalid input") print(match) #list(well_row=substr(x,1,1), well_col=as.integer(substr(x,2,nchar(x)))) } # you don't use this one. validate.and.catch.error <- function(x){ tryCatch(validate.single.well.input(x), error=function(e) NA) } # test = "A1:,D1" # validate.input.well.phrase (test) # function to validate each well phrase e.g. A1:D1, validate.input.well.phrase <- function(x){ match <- grepl("^[A-Ha-h]([0-9]|(1[0-2])):[A-Ha-h]([0-9]|(1[0-2]))$",x,perl=TRUE) if(!match) stop("invalid input") print(x) } # you don't use this one for now. validate.well.phrase.and.catch.error <- function(x){ tryCatch(validate.input.well.phrase(x), error=function(e) NA) }