How to write a function whose input is a vector and output is a character vector based on quantile...
up vote
0
down vote
favorite
I am writing a funcion whose input is a vector and output is a character vector of three levels: Below Avg, Avg, and Above Avg. I would like the character vector to be calucalted based on the 1st and 3rd quantiles of the vector given. When I call my function, only Below Avg returns which I understand why it returns, but do not know how to fix. Ideally I would like a new vector such that Below Avg corresponds to the values below the 1st quantile, Above Avg corresponds to values above the 3rd quantile, and Avg is everything in between.
x<-c(1:10)
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
if(vecrr<=lq){
k<-'Below Avg.'
} else if(vecrr>=uq){
k<-'Above Avg.'
} else{
k<-'Avg.'}
return(k)
}
y<-mapply(label_scale,x)
z<-sapply(x,label_scale)
r function quantile
add a comment |
up vote
0
down vote
favorite
I am writing a funcion whose input is a vector and output is a character vector of three levels: Below Avg, Avg, and Above Avg. I would like the character vector to be calucalted based on the 1st and 3rd quantiles of the vector given. When I call my function, only Below Avg returns which I understand why it returns, but do not know how to fix. Ideally I would like a new vector such that Below Avg corresponds to the values below the 1st quantile, Above Avg corresponds to values above the 3rd quantile, and Avg is everything in between.
x<-c(1:10)
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
if(vecrr<=lq){
k<-'Below Avg.'
} else if(vecrr>=uq){
k<-'Above Avg.'
} else{
k<-'Avg.'}
return(k)
}
y<-mapply(label_scale,x)
z<-sapply(x,label_scale)
r function quantile
Do you meanmapply(label_scale,x)
andsapply(x,label_scale)
? You posted those the other way around and it doesn't work at all.
– AntoniosK
2 days ago
My apologies. That has been fixed.
– Jack Armstrong
2 days ago
add a comment |
up vote
0
down vote
favorite
up vote
0
down vote
favorite
I am writing a funcion whose input is a vector and output is a character vector of three levels: Below Avg, Avg, and Above Avg. I would like the character vector to be calucalted based on the 1st and 3rd quantiles of the vector given. When I call my function, only Below Avg returns which I understand why it returns, but do not know how to fix. Ideally I would like a new vector such that Below Avg corresponds to the values below the 1st quantile, Above Avg corresponds to values above the 3rd quantile, and Avg is everything in between.
x<-c(1:10)
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
if(vecrr<=lq){
k<-'Below Avg.'
} else if(vecrr>=uq){
k<-'Above Avg.'
} else{
k<-'Avg.'}
return(k)
}
y<-mapply(label_scale,x)
z<-sapply(x,label_scale)
r function quantile
I am writing a funcion whose input is a vector and output is a character vector of three levels: Below Avg, Avg, and Above Avg. I would like the character vector to be calucalted based on the 1st and 3rd quantiles of the vector given. When I call my function, only Below Avg returns which I understand why it returns, but do not know how to fix. Ideally I would like a new vector such that Below Avg corresponds to the values below the 1st quantile, Above Avg corresponds to values above the 3rd quantile, and Avg is everything in between.
x<-c(1:10)
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
if(vecrr<=lq){
k<-'Below Avg.'
} else if(vecrr>=uq){
k<-'Above Avg.'
} else{
k<-'Avg.'}
return(k)
}
y<-mapply(label_scale,x)
z<-sapply(x,label_scale)
r function quantile
r function quantile
edited 2 days ago
asked 2 days ago
Jack Armstrong
288519
288519
Do you meanmapply(label_scale,x)
andsapply(x,label_scale)
? You posted those the other way around and it doesn't work at all.
– AntoniosK
2 days ago
My apologies. That has been fixed.
– Jack Armstrong
2 days ago
add a comment |
Do you meanmapply(label_scale,x)
andsapply(x,label_scale)
? You posted those the other way around and it doesn't work at all.
– AntoniosK
2 days ago
My apologies. That has been fixed.
– Jack Armstrong
2 days ago
Do you mean
mapply(label_scale,x)
and sapply(x,label_scale)
? You posted those the other way around and it doesn't work at all.– AntoniosK
2 days ago
Do you mean
mapply(label_scale,x)
and sapply(x,label_scale)
? You posted those the other way around and it doesn't work at all.– AntoniosK
2 days ago
My apologies. That has been fixed.
– Jack Armstrong
2 days ago
My apologies. That has been fixed.
– Jack Armstrong
2 days ago
add a comment |
2 Answers
2
active
oldest
votes
up vote
1
down vote
accepted
Your problem is that you apply your function to each one of the elements of your vector and by default a given value is always equal to the quantile of that value and your process will return Below Avg
for each one of the vector elements. (Eg. x == quantile(x, 0.25)
will always return TRUE).
You should use ifelse
inside your function, which is vectorised:
# example vector
x<-c(1:10)
# function
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
ifelse(vecrr<=lq, 'Below Avg.', ifelse(vecrr>=uq, 'Above Avg.', 'Avg.'))
}
# use function on a vector
label_scale(x)
# [1] "Below Avg." "Below Avg." "Below Avg." "Avg." "Avg." "Avg." "Avg." "Above Avg."
# [9] "Above Avg." "Above Avg."
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
add a comment |
up vote
0
down vote
I would use cut and quantile in this situation:
x <- c(1:10)
x.char <- cut(x, quantile(x, c(0,.25,.75,1)), include.lowest = T, labels = c('Below Avg.', 'Avg.','Above Avg.'))
x.char
[1] Below Avg. Below Avg. Below Avg. Avg. Avg. Avg. Avg.
[8] Above Avg. Above Avg. Above Avg.
Levels: Below Avg. Avg. Above Avg.
add a comment |
2 Answers
2
active
oldest
votes
2 Answers
2
active
oldest
votes
active
oldest
votes
active
oldest
votes
up vote
1
down vote
accepted
Your problem is that you apply your function to each one of the elements of your vector and by default a given value is always equal to the quantile of that value and your process will return Below Avg
for each one of the vector elements. (Eg. x == quantile(x, 0.25)
will always return TRUE).
You should use ifelse
inside your function, which is vectorised:
# example vector
x<-c(1:10)
# function
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
ifelse(vecrr<=lq, 'Below Avg.', ifelse(vecrr>=uq, 'Above Avg.', 'Avg.'))
}
# use function on a vector
label_scale(x)
# [1] "Below Avg." "Below Avg." "Below Avg." "Avg." "Avg." "Avg." "Avg." "Above Avg."
# [9] "Above Avg." "Above Avg."
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
add a comment |
up vote
1
down vote
accepted
Your problem is that you apply your function to each one of the elements of your vector and by default a given value is always equal to the quantile of that value and your process will return Below Avg
for each one of the vector elements. (Eg. x == quantile(x, 0.25)
will always return TRUE).
You should use ifelse
inside your function, which is vectorised:
# example vector
x<-c(1:10)
# function
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
ifelse(vecrr<=lq, 'Below Avg.', ifelse(vecrr>=uq, 'Above Avg.', 'Avg.'))
}
# use function on a vector
label_scale(x)
# [1] "Below Avg." "Below Avg." "Below Avg." "Avg." "Avg." "Avg." "Avg." "Above Avg."
# [9] "Above Avg." "Above Avg."
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
add a comment |
up vote
1
down vote
accepted
up vote
1
down vote
accepted
Your problem is that you apply your function to each one of the elements of your vector and by default a given value is always equal to the quantile of that value and your process will return Below Avg
for each one of the vector elements. (Eg. x == quantile(x, 0.25)
will always return TRUE).
You should use ifelse
inside your function, which is vectorised:
# example vector
x<-c(1:10)
# function
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
ifelse(vecrr<=lq, 'Below Avg.', ifelse(vecrr>=uq, 'Above Avg.', 'Avg.'))
}
# use function on a vector
label_scale(x)
# [1] "Below Avg." "Below Avg." "Below Avg." "Avg." "Avg." "Avg." "Avg." "Above Avg."
# [9] "Above Avg." "Above Avg."
Your problem is that you apply your function to each one of the elements of your vector and by default a given value is always equal to the quantile of that value and your process will return Below Avg
for each one of the vector elements. (Eg. x == quantile(x, 0.25)
will always return TRUE).
You should use ifelse
inside your function, which is vectorised:
# example vector
x<-c(1:10)
# function
label_scale<-function(vecrr){
lq<-quantile(vecrr,0.25)
uq<-quantile(vecrr,0.75)
ifelse(vecrr<=lq, 'Below Avg.', ifelse(vecrr>=uq, 'Above Avg.', 'Avg.'))
}
# use function on a vector
label_scale(x)
# [1] "Below Avg." "Below Avg." "Below Avg." "Avg." "Avg." "Avg." "Avg." "Above Avg."
# [9] "Above Avg." "Above Avg."
edited 2 days ago
answered 2 days ago
AntoniosK
12.1k1822
12.1k1822
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
add a comment |
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
This gets more complicated with more levels. The cut function is specifically designed for converting numeric vectors into character/factor vectors - see my answer.
– rookie
2 days ago
add a comment |
up vote
0
down vote
I would use cut and quantile in this situation:
x <- c(1:10)
x.char <- cut(x, quantile(x, c(0,.25,.75,1)), include.lowest = T, labels = c('Below Avg.', 'Avg.','Above Avg.'))
x.char
[1] Below Avg. Below Avg. Below Avg. Avg. Avg. Avg. Avg.
[8] Above Avg. Above Avg. Above Avg.
Levels: Below Avg. Avg. Above Avg.
add a comment |
up vote
0
down vote
I would use cut and quantile in this situation:
x <- c(1:10)
x.char <- cut(x, quantile(x, c(0,.25,.75,1)), include.lowest = T, labels = c('Below Avg.', 'Avg.','Above Avg.'))
x.char
[1] Below Avg. Below Avg. Below Avg. Avg. Avg. Avg. Avg.
[8] Above Avg. Above Avg. Above Avg.
Levels: Below Avg. Avg. Above Avg.
add a comment |
up vote
0
down vote
up vote
0
down vote
I would use cut and quantile in this situation:
x <- c(1:10)
x.char <- cut(x, quantile(x, c(0,.25,.75,1)), include.lowest = T, labels = c('Below Avg.', 'Avg.','Above Avg.'))
x.char
[1] Below Avg. Below Avg. Below Avg. Avg. Avg. Avg. Avg.
[8] Above Avg. Above Avg. Above Avg.
Levels: Below Avg. Avg. Above Avg.
I would use cut and quantile in this situation:
x <- c(1:10)
x.char <- cut(x, quantile(x, c(0,.25,.75,1)), include.lowest = T, labels = c('Below Avg.', 'Avg.','Above Avg.'))
x.char
[1] Below Avg. Below Avg. Below Avg. Avg. Avg. Avg. Avg.
[8] Above Avg. Above Avg. Above Avg.
Levels: Below Avg. Avg. Above Avg.
edited 2 days ago
answered 2 days ago
rookie
663
663
add a comment |
add a comment |
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53410346%2fhow-to-write-a-function-whose-input-is-a-vector-and-output-is-a-character-vector%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Do you mean
mapply(label_scale,x)
andsapply(x,label_scale)
? You posted those the other way around and it doesn't work at all.– AntoniosK
2 days ago
My apologies. That has been fixed.
– Jack Armstrong
2 days ago