R function for Fizzbuzz and Fibonacci number - r

i am tasked with the following two questions, however for some reason my codes dont work.
Problem 1
Write a function (named FizzBuzz_function) that takes a number from the user (named n) and prints the numbers from 1 to n. However, for multiples of three print “Fizz” instead of the number and for the multiples of five print “Buzz”. For numbers which are multiples of both three and five print “FizzBuzz”.
Problem 2
Write a function that takes a number from the user (named n) and returns nth Fibonacci number.
Please check your function: When n is 20, the Fibonacci number (F20) is 6765 (I assume F1=1, F2=1).
Here are my answers but I am not getting any outputs
1.
n <- readline(prompt="Enter your number: ")
# define the function
fizz_buzz <- FizzBuzz_function(n){
if(n%%3 == 0 & n%%5 == 0) {
print('FizzBuzz')
}
else if(n%%3 == 0) {
print('Fizz')
}
else if (n%%5 == 0){
print('Buzz')
}
else {
print(n)
}
}
n <- readline(prompt="Enter your number: ")
vast=function(n){
vast=vector()
vast[1]=1
vast[2]=1
for(i in 3:n){vast[i]=vast[i-1]+vast[i-2]}
return(vast)
}

Related

Attempting a for loop in R

x <- 1:19
count <- 0
for (i in x) {
if atranspose * T5_5_FBEETLES[i, 3:6]>cutoff
count=count+1
}
print(count)
Hello, I am trying to do a for loop in R. In this for loop, I am multiplying a 1x4 matrix (atranspose in this case) and the third through sixth columns of a table (the table is T5_5_FBEETLES in this case) row by row (hence the i in x, so going through the first 19 rows) and I'm comparing it to a number with the variable name of cutoff. If the multiplication ends up with something greater than the cutoff number, I want count to increase by 1. I know from doing this by hand that by the end count should be 19, but for whatever reason my for loop returns 1 for my count variable and I keep getting these two errors:
unexpected symbol in:
"for (i in x) {
if atranspose"
unexpected '}' in "}"
Can anyone explain to me why these two errors are occurring, and how I can fix up my for loop so that it can return the correct count?
You are getting an error because your if statement crosses a line and thus needs some curly braces:
x <- 1:19
count <- 0
for (i in x) {
if (atranspose * T5_5_FBEETLES[i, 3:6]>cutoff) {
count=count+1
}
}
print(count)
This will then give you another error because the logical check of the if statement will return a vector, so it needs to be wrapped in an any:
x <- 1:19
count <- 0
for (i in x) {
if (any(atranspose * T5_5_FBEETLES[i, 3:6]>cutoff)) {
count=count+1
}
}
print(count)

Difficulty with recursively adding non-whole number

I am new to R and I am having difficulty with a simple recursion function. I initialize a variable, x to .1 and then make a call to a recursive function in which if x is not equal to the user-input number, it will add .1 to x and recursively call the function again. If x is greater than the input number, the function returns an error message.
I have tried setting x to a whole number, mainly 1 and then trying to evaluate the function. This process works, so I figure that there is an issue of adding decimal numbers to each other and then evaluating their equality with a whole number.
u<-function(a)
{
#Initialize r
x<-.1
#Call to recursive method
v(a, x)
}
#Recursive function
v<-function(a, x)
{
#Check for current value of a and r
print(a)
print(x)
if(a==x) {
return("Yes")
}
else if(a < x) {
return("Error!")
}
else{
x<-x+.1
v(a, x)
}
}
When I set a to 1, I would expect the function to return "Yes" after recursing until x is equal to 1 as well. However, this is not the case. The function then recurses once more, setting x to 1.1 and returns the message "Error!".
I think you are running into issues with floating point precision. If you use a function designed to check equality while accounting for floating point precision, like dplyr::near(), the function gives the expected result:
v<-function(a, x)
{
#Check for current value of a and r
print(a)
print(x)
if(dplyr::near(a, x)) {
return("Yes")
}
else if(a < x) {
return("Error!")
}
else{
x<-x+.1
v(a, x)
}
}

In R, how to read multiple integers from user prompt?

I need to create a vector with multiple inputs (integers) from user.
The intent is to create a list and verify if it has a mode and where is its median.
I am using this code:
ReadVector <- function()
{
x <- 0
while(x<16) {
n <- readline(prompt="Input one integer: ")
return(as.integer(n))
VectorUser <- c(n)
x <- x+1
}
print(VectorUser)
}
ReadVector()
And I can only get one integer, I dont know if my mistake is in the while loop or(and) in the concatenate command after it. Can you help me?
Does this work for you?
ReadVector <- function()
{
x <- 0
myvector = vector()
while(x<16) {
n <- readline(prompt="Input one integer: ")
myvector = c(myvector,n)
x <- x+1
}
return (as.integer(myvector))
}
You need yo save your values in a vector, and keep it (without returning inside the loop), until you completed it.
Hope it helps
ff=function(){
d=c()
while (TRUE){
int = readline('ENTER to quit > ')
if(nchar(int)==0) {
if(length(d)>0)cat("The numbers you entered are:",d)
else(cat("You did not enter any number!!"));break}
else{
value=suppressWarnings(as.integer(int))
if(!is.na(value)){cat(value);d=c(d,value)} else cat(ran[sample(6,1)])
}}
ff()

Error message in Bubble sort code in R language

I did some programming work on R language to do the bubble sort. Sometimes it works perfectly without any error message, but sometimes, it shows "Error in if (x[i] > x[i + 1]) { : argument is of length zero". Can any one help me check whats wrong with it? I have attached my code below
example <- function(x) {
n <- length(x)
repeat {
hasChanged <- FALSE
n <- n - 1
for(i in 1:n) {
if ( x[i] > x[i+1] ) {
temp <- x[i]
x[i] <- x[i+1]
x[i+1] <- temp
hasChanged <- TRUE
cat("The current Vector is", x ,"\n")
}
}
if ( !hasChanged ) break;
}
}
x <-sample(1:10,5)
cat("The original Vector is", x ,"\n")
example(x)
The error occurs because you are iteratively decreasing n. Depending on the original vector's order (or lack thereof), n can reach the value of 1 after the last change. In that case, a further reduction of n in the next iteration step addresses the value x[0], which is undefined.
With a minimal correction your code will work properly, without giving error messages. Try to replace the line
if ( !hasChanged ) break;
with
if ( !hasChanged | n==1 ) break
Basically you have two termination criteria: Either nothing has been changed in the previous iteration or n is equal to one. In both cases, a further iteration won't change the vector since it is already ordered.
By the way, in R programming you don't need a semicolon at the end of a command. It is tolerated/ignored by the interpreter, but it clutters the code and is not considered good programming style.
Hope this helps.

Finding duplicate values in r

So, In a string containing multiple 1's,
Now, it is possible that, the number
'1'
appears at several positions, let's say, at multiple positions. What I want is
(3)
This is not a complete answer, but some ideas (partly based on comments):
z <- "1101101101"
zz <- as.numeric(strsplit(z,"")[[1]])
Compute autocorrelation function and draw plot: in this case I'm getting the periodicity=3 pretty crudely as the first point at which there is an increase followed by a decrease ...
a1 <- acf(zz)
first.peak <- which(diff(sign(diff(a1$acf[,,1])))==-2)[1]
Now we know the periodicity is 3; create runs of 3 with embed() and analyze their similarities:
ee <- embed(zz,first.peak)
pp <- apply(ee,1,paste,collapse="")
mm <- outer(pp,pp,"==")
aa <- apply(mm[!duplicated(mm),],1,which)
sapply(aa,length) ## 3 3 2 ## number of repeats
sapply(aa,function(x) unique(diff(x))) ## 3 3 3
The following code does exactly what you ask for. Try it with str_groups('1101101101'). It returns a list of 3-vectors. Note that the first triple is (1, 3, 4) because the character at the 10th position is also a 1.
Final version, optimized and without errors
str_groups <- function (s) {
digits <- as.numeric(strsplit(s, '')[[1]])
index1 <- which(digits == 1)
len <- length(digits)
back <- length(index1)
if (back == 0) return(list())
maxpitch <- (len - 1) %/% 2
patterns <- matrix(0, len, maxpitch)
result <- list()
for (pitch in 1:maxpitch) {
divisors <- which(pitch %% 1:(pitch %/% 2) == 0)
while (index1[back] > len - 2 * pitch) {
back <- back - 1
if (back == 0) return(result)
}
for (startpos in index1[1:back]) {
if (patterns[startpos, pitch] != 0) next
pos <- seq(startpos, len, pitch)
if (digits[pos[2]] != 1 || digits[pos[3]] != 1) next
repeats <- length(pos)
if (repeats > 3) for (i in 4:repeats) {
if (digits[pos[i]] != 1) {
repeats <- i - 1
break
}
}
continue <- F
for (subpitch in divisors) {
sublen <- patterns[startpos, subpitch]
if (sublen > pitch / subpitch * (repeats - 1)) {
continue <- T
break
}
}
if (continue) next
for (i in 1:repeats) patterns[pos[i], pitch] <- repeats - i + 1
result <- append(result, list(c(startpos, pitch, repeats)))
}
}
return(result)
}
Note: this algorithm has roughly quadratic runtime complexity, so if you make your strings twice as long, it will take four times as much time to find all patterns on average.
Pseudocode version
To aid understanding of the code. For particulars of R functions such as which, consult the R online documentation, for example by running ?which on the R command line.
PROCEDURE str_groups WITH INPUT $s (a string of the form /(0|1)*/):
digits := array containing the digits in $s
index1 := positions of the digits in $s that are equal to 1
len := pointer to last item in $digits
back := pointer to last item in $index1
IF there are no items in $index1, EXIT WITH empty list
maxpitch := the greatest possible interval between 1-digits, given $len
patterns := array with $len rows and $maxpitch columns, initially all zero
result := array of triplets, initially empty
FOR EACH possible $pitch FROM 1 TO $maxpitch:
divisors := array of divisors of $pitch (including 1, excluding $pitch)
UPDATE $back TO the last position at which a pattern could start;
IF no such position remains, EXIT WITH result
FOR EACH possible $startpos IN $index1 up to $back:
IF $startpos is marked as part of a pattern, SKIP TO NEXT $startpos
pos := possible positions of pattern members given $startpos, $pitch
IF either the 2nd or 3rd $pos is not 1, SKIP TO NEXT $startpos
repeats := the number of positions in $pos
IF there are more than 3 positions in $pos THEN
count how long the pattern continues
UPDATE $repeats TO the length of the pattern
END IF (more than 3 positions)
FOR EACH possible $subpitch IN $divisors:
check $patterns for pattern with interval $subpitch at $startpos
IF such a pattern is found AND it envelopes the current pattern,
SKIP TO NEXT $startpos
(using helper variable $continue to cross two loop levels)
END IF (pattern found)
END FOR (subpitch)
FOR EACH consecutive position IN the pattern:
UPDATE $patterns at row of position and column of $pitch TO ...
... the remaining length of the pattern at that position
END FOR (position)
APPEND the triplet ($startpos, $pitch, $repeats) TO $result
END FOR (startpos)
END FOR (pitch)
EXIT WITH $result
END PROCEDURE (str_groups)
Perhaps the following route will help:
Convert string to a vector of integers characters
v <- as.integer(strsplit(s, "")[[1]])
Repeatedly convert this vector to matrices of varying number of rows...
m <- matrix(v, nrow=...)
...and use rle to find relevant patterns in the rows of the matrix m:
rle(m[1, ]); rle(m[2, ]); ...

Resources