Как использовать lapply с условием в R, чтобы каждый раз соответствовать только одному элементу - PullRequest
0 голосов
/ 02 июля 2018

Предположим, у меня есть два вектора. Предположим далее, что я хотел бы, чтобы моя функция принимала только одно значение каждого вектора и возвращала мне выходные данные. Затем я хотел бы, чтобы другая функция проверяла значения каждого прогона. Если результат предыдущего прогона меньше, чем новый. Затем я хотел бы, чтобы моя функция остановилась и вернула мне все предыдущие значения. Моя оригинальная функция очень сложна (модели оценки). Поэтому я пытаюсь привести пример, чтобы объяснить мою идею.

Предположим, что у меня есть эти два вектора:

set.seed(123)
x <- rnorm(1:20)
y <- rnorm(1:20)

Затем я хотел бы написать функцию, которая принимает только одно значение каждого вектора и умножает их. Затем верните мне вывод. Затем я хотел бы, чтобы функция проверяла, меньше ли предыдущее умножение, чем новое. Если да, то остановись и верни мне все предыдущие умножения.

Я попробовал это: Однако эта функция принимает все значения сразу и возвращает мне список умножения. Я думал об использовании lapply, чтобы соответствовать одному элементу за раз, но я не знаю, как работать с условиями.

myfun <- function(x, y, n){
    multi <- list()
    for ( i in 1:n){
        multi[[i]] <- x[[i]]*y[[i]]
    }
    return(multi)
}
myfun(x,y,10)

Вот еще одна попытка

 x <- rnorm(1:20)
y <- rnorm(1:20)
myfun <- function(x, y){
            multi <- x*y

    return(multi)
}

Это первая функция. Я хотел бы запустить его элемент за элементом. Каждый раз я хотел бы, чтобы он возвращал мне только один результат умножения. Затем другая функция (функция-обертка) проверяет результат. Если второй выход первой функции (функция умножения) больше, чем первая, то остановите, в противном случае продолжайте.

1 Ответ

0 голосов
/ 02 июля 2018

Я хотел бы написать функцию, которая принимает только одно значение каждого вектора и умножает их. Затем верните мне вывод. Затем я хотел бы, чтобы функция проверяла, меньше ли предыдущее умножение, чем новое.

Я бы хотел умножение в отдельной функции. Затем я хотел бы проверить его вывод. Итак, у меня должна быть функция согревания.

Вы можете применить цикл for с условием остановки, аналогично тому, что у вас уже было:

# example input
set.seed(123)
x <- rnorm(1:20)
y <- rnorm(1:20)

# example function
f = function(xi, yi) xi*yi

# wrapper
stopifnot(length(x) == length(y))
res = vector(length(x), mode="list")

for (i in seq_along(x)){
  res[[i]] = f(x[[i]], y[[i]])
  if (i > 1L && res[[i]] > res[[i-1L]]) break
}

res[seq_len(i)]

Комментарии:

  • Лучше заранее определить максимальную длину, которая может понадобиться res (здесь length(x)), чем расширять ее в цикле.
  • Для этой функции (умножение) нет веских оснований для поэтапного выполнения. Функция умножения R векторизована и быстра.
  • Вам не нужно использовать вывод класса списка для этой функции, поскольку она возвращает double; res = double(length(x)) также должно работать.
  • Вам не нужно использовать методы доступа в виде списков для x, y и res, если не задействованы списки; res[i] = f(x[i], y[i]) должно работать и т. Д.
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...