Функции в программировании на R (с примером)

Содержание:

Anonim

Что такое функция в R?

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

Функция должна быть

  • написано для выполнения указанной задачи
  • может включать или не включать аргументы
  • содержать тело
  • может возвращать или не возвращать одно или несколько значений.

Общий подход к функции состоит в том, чтобы использовать часть аргумента в качестве входных данных , подавать часть тела и, наконец, возвращать результат . Синтаксис функции следующий:

function (arglist) {#Function body}

В этом уроке мы узнаем

  • Важные встроенные функции
  • Общие функции
  • Математические функции
  • Статистические функции
  • Написать функцию в R
  • Когда писать функцию?
  • Функции с условием

Важные встроенные функции

В R. есть много встроенных функций. R сопоставляет ваши входные параметры со своими аргументами функции либо по значению, либо по позиции, а затем выполняет тело функции. Аргументы функции могут иметь значения по умолчанию: если вы не укажете эти аргументы, R примет значение по умолчанию.

Примечание : можно увидеть исходный код функции, запустив имя самой функции в консоли.

Мы увидим три группы функций в действии

  • Общая функция
  • Математическая функция
  • Статистическая функция

Общие функции

Мы уже знакомы с такими общими функциями, как cbind (), rbind (), range (), sort (), order (). Каждая из этих функций имеет определенную задачу, принимает аргументы для возврата вывода. Ниже приведены важные функции, которые необходимо знать:

функция diff ()

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

Примечание : нам часто нужно создавать случайные данные, но для обучения и сравнения мы хотим, чтобы числа были одинаковыми на разных машинах. Чтобы гарантировать, что все мы генерируем одни и те же данные, мы используем функцию set.seed () с произвольными значениями 123. Функция set.seed () генерируется с помощью процесса генератора псевдослучайных чисел, который заставляет все современные компьютеры иметь одинаковую последовательность. номеров. Если мы не будем использовать функцию set.seed (), у всех будет разная последовательность чисел.

set.seed(123)## Create the datax = rnorm(1000)ts <- cumsum(x)## Stationary the seriediff_ts <- diff(ts)par(mfrow=c(1,2))## Plot the seriesplot(ts,)plot(diff(ts),)

функция length ()

Во многих случаях нам нужно знать длину вектора для вычисления или использования в цикле for. Функция length () подсчитывает количество строк в векторе x. Следующие коды импортируют набор данных автомобилей и возвращают количество строк.

Примечание : length () возвращает количество элементов в векторе. Если функция передается в матрицу или фрейм данных, возвращается количество столбцов.

dt <- cars## number columnslength(dt)

Выход:

## [1] 1
## number rowslength(dt[,1])

Выход:

## [1] 50

Математические функции

В R есть набор математических функций.

Оператор Описание
абс (х) Принимает абсолютное значение x
журнал (х, основание = у) Логарифмирует x по основанию y; если основание не указано, возвращает натуральный логарифм
ехр (х) Возвращает экспоненту x.
sqrt (х) Возвращает квадратный корень из x.
факториал (x) Возвращает факториал x (x!)
# sequence of number from 44 to 55 both including incremented by 1x_vector <- seq(45,55, by = 1)#logarithmlog(x_vector)

Выход:

## [1] 3.806662 3.828641 3.850148 3.871201 3.891820 3.912023 3.931826## [8] 3.951244 3.970292 3.988984 4.007333
#exponentialexp(x_vector)
#squared rootsqrt(x_vector)

Выход:

## [1] 6.708204 6.782330 6.855655 6.928203 7.000000 7.071068 7.141428## [8] 7.211103 7.280110 7.348469 7.416198
#factorialfactorial(x_vector)

Выход:

## [1] 1.196222e+56 5.502622e+57 2.586232e+59 1.241392e+61 6.082819e+62## [6] 3.041409e+64 1.551119e+66 8.065818e+67 4.274883e+69 2.308437e+71## [11] 1.269640e+73

Статистические функции

Стандартная установка R содержит широкий набор статистических функций. В этом уроке мы кратко рассмотрим самую важную функцию…

Основные статистические функции

Оператор

Описание

среднее (х)

Среднее значение x

медиана (х)

Медиана x

var (x)

Дисперсия x

sd (x)

Стандартное отклонение x

масштаб (х)

Стандартные баллы (z-баллы) x

квантиль (x)

Квартили x

резюме (x)

Сводка x: среднее, минимальное, максимальное и т. Д.

speed <- dt$speedspeed# Mean speed of cars datasetmean(speed)

Выход:

## [1] 15.4
# Median speed of cars datasetmedian(speed)

Выход:

## [1] 15
# Variance speed of cars datasetvar(speed)

Выход:

## [1] 27.95918
# Standard deviation speed of cars datasetsd(speed)

Выход:

## [1] 5.287644
# Standardize vector speed of cars datasethead(scale(speed), 5)

Выход:

## [,1]## [1,] -2.155969## [2,] -2.155969## [3,] -1.588609## [4,] -1.588609## [5,] -1.399489
# Quantile speed of cars datasetquantile(speed)

Выход:

## 0% 25% 50% 75% 100%## 4 12 15 19 25
# Summary speed of cars datasetsummary(speed)

Выход:

## Min. 1st Qu. Median Mean 3rd Qu. Max.## 4.0 12.0 15.0 15.4 19.0 25.0

К этому моменту мы изучили множество встроенных функций R.

Примечание : будьте осторожны с классом аргумента, то есть числовым, логическим или строковым. Например, если нам нужно передать строковое значение, нам нужно заключить строку в кавычки: «ABC».

Написать функцию в R

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

function.name <- function(arguments){computations on the argumentssome other code}

Примечание . Рекомендуется называть пользовательскую функцию отличным от встроенной функции. Это позволяет избежать путаницы.

Функция с одним аргументом

В следующем фрагменте мы определяем простую квадратную функцию. Функция принимает значение и возвращает квадрат значения.

square_function<- function(n){# compute the square of integer `n`n^2}# calling the function and passing value 4square_function(4)

Пояснение к коду:

  • Функция называется square_function; его можно называть как угодно.
  • Он получает аргумент «n». Мы не указали тип переменной, чтобы пользователь мог передать целое число, вектор или матрицу.
  • Функция принимает на входе "n" и возвращает квадрат ввода.

    Когда вы закончите использовать функцию, мы можем удалить ее с помощью функции rm ().

# после создания функции

rm(square_function)square_function

На консоли мы видим сообщение об ошибке: Ошибка: объект 'square_function' не найден, что говорит о том, что функция не существует.

Оценка окружающей среды

В R среда представляет собой набор объектов, таких как функции, переменные, фрейм данных и т. Д.

R открывает среду каждый раз при запросе Rstudio.

Доступная среда верхнего уровня - это глобальная среда , называемая R_GlobalEnv. И у нас есть местная среда.

Мы можем перечислить содержимое текущего окружения.

ls(environment())

Выход

## [1] "diff_ts" "dt" "speed" "square_function"## [5] "ts" "x" "x_vector"

Вы можете увидеть все переменные и функции, созданные в R_GlobalEnv.

Приведенный выше список будет отличаться для вас в зависимости от исторического кода, который вы выполняете в R Studio.

Обратите внимание, что n, аргумент функции square_function не находится в этой глобальной среде .

Для каждой функции создается новая среда. В приведенном выше примере функция square_function () создает новую среду внутри глобальной среды.

Чтобы прояснить разницу между глобальной и локальной средой , давайте рассмотрим следующий пример.

Эта функция принимает значение x в качестве аргумента и добавляет его к определению y вне и внутри функции.

Функция f возвращает результат 15. Это связано с тем, что y определен в глобальной среде. Любая переменная, определенная в глобальной среде, может использоваться локально. Переменная y имеет значение 10 во время всех вызовов функций и доступна в любое время.

Посмотрим, что произойдет, если переменная y определена внутри функции.

Нам нужно отбросить `y` перед запуском этого кода с помощью rm r

Вывод также равен 15, когда мы вызываем f (5), но возвращает ошибку, когда мы пытаемся напечатать значение y. Переменная y не находится в глобальной среде.

Наконец, R использует самое последнее определение переменной для передачи внутри тела функции. Рассмотрим следующий пример:

R игнорирует значения y, определенные вне функции, потому что мы явно создали переменную y внутри тела функции.

Функция с несколькими аргументами

Мы можем написать функцию с более чем одним аргументом. Рассмотрим функцию под названием «раз». Это простая функция умножения двух переменных.

times <- function(x,y) {x*y}times(2,4)

Выход:

## [1] 8

Когда писать функцию?

Специалисту по анализу данных необходимо выполнять множество повторяющихся задач. В большинстве случаев мы многократно копируем и вставляем фрагменты кода. Например, перед запуском алгоритма машинного обучения настоятельно рекомендуется нормализовать переменную. Формула нормализации переменной:

Мы уже знаем, как использовать функции min () и max () в R. Мы используем библиотеку tibble для создания фрейма данных. Tibble пока что является самой удобной функцией для создания набора данных с нуля.

library(tibble)# Create a data framedata_frame <- tibble(c1 = rnorm(50, 5, 1.5),c2 = rnorm(50, 5, 1.5),c3 = rnorm(50, 5, 1.5),)

Мы выполним два шага, чтобы вычислить функцию, описанную выше. На первом этапе мы создадим переменную c1_norm, которая является масштабированием c1. На втором шаге мы просто копируем и вставляем код c1_norm и меняем его с помощью c2 и c3.

Деталь функции со столбцом c1:

Номинатор:: data_frame $ c1 -min (data_frame $ c1))

Знаменатель: макс (кадр_данных $ c1) -мин (кадр_данных $ c1))

Следовательно, мы можем разделить их, чтобы получить нормализованное значение столбца c1:

(data_frame$c1 -min(data_frame$c1))/(max(data_frame$c1)-min(data_frame$c1)) 

Мы можем создать c1_norm, c2_norm и c3_norm:

Create c1_norm: rescaling of c1data_frame$c1_norm <- (data_frame$c1 -min(data_frame$c1))/(max(data_frame$c1)-min(data_frame$c1))# show the first five valueshead(data_frame$c1_norm, 5)

Выход:

## [1] 0.3400113 0.4198788 0.8524394 0.4925860 0.5067991

Оно работает. Мы можем копировать и вставлять

data_frame$c1_norm <- (data_frame$c1 -min(data_frame$c1))/(max(data_frame$c1)-min(data_frame$c1))

затем измените c1_norm на c2_norm и c1 на c2. То же самое делаем для создания c3_norm

data_frame$c2_norm <- (data_frame$c2 - min(data_frame$c2))/(max(data_frame$c2)-min(data_frame$c2))data_frame$c3_norm <- (data_frame$c3 - min(data_frame$c3))/(max(data_frame$c3)-min(data_frame$c3))

Мы идеально изменили масштаб переменных c1, c2 и c3.

Однако этот метод подвержен ошибкам. Мы могли скопировать и забыть изменить имя столбца после вставки. Поэтому рекомендуется писать функцию каждый раз, когда вам нужно вставить один и тот же код более двух раз. Мы можем преобразовать код в формулу и вызывать ее, когда это необходимо. Чтобы написать собственную функцию, нам нужно предоставить:

  • Название: нормализовать.
  • количество аргументов: нам нужен только один аргумент - столбец, который мы используем в наших вычислениях.
  • Тело: это просто формула, которую мы хотим вернуть.

Мы продолжим шаг за шагом, чтобы создать функцию normalize.

Шаг 1) Создаем номинатора , который есть. В R мы можем сохранить номинатор в такой переменной:

nominator <- x-min(x)

Шаг 2) Вычислим знаменатель: . Мы можем воспроизвести идею шага 1 и сохранить вычисление в переменной:

denominator <- max(x)-min(x)

Шаг 3) Производим деление на знаменатель и знаменатель.

normalize <- nominator/denominator

Шаг 4) Чтобы вернуть значение вызывающей функции, нам нужно передать нормализацию внутри return (), чтобы получить результат функции.

return(normalize)

Шаг 5) Мы готовы использовать функцию, обернув все внутри скобки.

normalize <- function(x){# step 1: create the nominatornominator <- x-min(x)# step 2: create the denominatordenominator <- max(x)-min(x)# step 3: divide nominator by denominatornormalize <- nominator/denominator# return the valuereturn(normalize)}

Давайте протестируем нашу функцию с переменной c1:

normalize(data_frame$c1)

Работает отлично. Мы создали нашу первую функцию.

Функции - это более комплексный способ выполнения повторяющейся задачи. Мы можем использовать формулу нормализации для разных столбцов, как показано ниже:

data_frame$c1_norm_function <- normalize (data_frame$c1)data_frame$c2_norm_function <- normalize (data_frame$c2)data_frame$c3_norm_function <- normalize (data_frame$c3)

Несмотря на то, что пример прост, мы можем сделать вывод о силе формулы. Приведенный выше код легче читать и особенно избегать ошибок при вставке кодов.

Функции с условием

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

В задачах машинного обучения нам нужно разделить набор данных между набором поездов и набором тестов. Набор поездов позволяет алгоритму учиться на данных. Чтобы проверить производительность нашей модели, мы можем использовать набор тестов, чтобы получить показатель производительности. В R нет функции для создания двух наборов данных. Для этого мы можем написать нашу собственную функцию. Наша функция принимает два аргумента и называется split_data (). Идея проста: мы умножаем длину набора данных (то есть количество наблюдений) на 0,8. Например, если мы хотим разделить набор данных 80/20, а наш набор данных содержит 100 строк, тогда наша функция умножит 0,8 * 100 = 80. 80 строк будут выбраны, чтобы стать нашими обучающими данными.

Мы будем использовать набор данных о качестве воздуха для тестирования нашей пользовательской функции. Набор данных о качестве воздуха состоит из 153 строк. Мы можем увидеть это с помощью кода ниже:

nrow(airquality)

Выход:

## [1] 153 

Мы будем действовать следующим образом:

split_data <- function(df, train = TRUE)Arguments:-df: Define the dataset-train: Specify if the function returns the train set or test set. By default, set to TRUE

У нашей функции два аргумента. Цепочка аргументов - это логический параметр. Если установлено значение ИСТИНА, наша функция создает набор данных поезда, в противном случае - тестовый набор данных.

Мы можем действовать так же, как и с функцией normalize (). Мы пишем код, как если бы это был только одноразовый код, а затем оборачиваем все с условием в тело, чтобы создать функцию.

Шаг 1:

Нам нужно вычислить длину набора данных. Это делается с помощью функции nrow (). Nrow возвращает общее количество строк в наборе данных. Мы называем переменную длину.

length<- nrow(airquality)length

Выход:

## [1] 153

Шаг 2:

Умножаем длину на 0,8. Он вернет количество строк для выбора. Должно быть 153 * 0,8 = 122,4

total_row <- length*0.8total_row

Выход:

## [1] 122.4

Мы хотим выбрать 122 строки из 153 в наборе данных о качестве воздуха. Создаем список, содержащий значения от 1 до total_row. Мы сохраняем результат в переменной под названием split.

split <- 1:total_rowsplit[1:5] 

Выход:

## [1] 1 2 3 4 5

split выбирает первые 122 строки из набора данных. Например, мы видим, что наша переменная split собирает значения 1, 2, 3, 4, 5 и так далее. Эти значения будут индексом, когда мы выберем строки для возврата.

Шаг 3:

Нам нужно выбрать строки в наборе данных о качестве воздуха на основе значений, хранящихся в переменной разделения. Делается это так:

train_df <- airquality[split, ]head(train_df)

Выход:

##[1] Ozone Solar.R Wind Temp Month Day##[2] 51 13 137 10.3 76 6 20##[3] 15 18 65 13.2 58 5 15##[4] 64 32 236 9.2 81 7 3##[5] 27 NA NA 8.0 57 5 27##[6] 58 NA 47 10.3 73 6 27##[7] 44 23 148 8.0 82 6 13

Шаг 4:

Мы можем создать тестовый набор данных, используя оставшиеся строки, 123: 153. Это делается с помощью - перед разделением.

test_df <- airquality[-split, ]head(test_df)

Выход:

##[1] Ozone Solar.R Wind Temp Month Day##[2] 123 85 188 6.3 94 8 31##[3] 124 96 167 6.9 91 9 1##[4] 125 78 197 5.1 92 9 2##[5] 126 73 183 2.8 93 9 3##[6] 127 91 189 4.6 93 9 4##[7] 128 47 95 7.4 87 9 5

Шаг 5:

Мы можем создать условие внутри тела функции. Помните, что у нас есть поезд аргументов, который является логическим значением TRUE по умолчанию, чтобы вернуть набор поездов. Для создания условия мы используем синтаксис if:

if (train ==TRUE){train_df <- airquality[split, ]return(train)} else {test_df <- airquality[-split, ]return(test)}

Вот и все, мы можем написать функцию. Нам нужно только изменить качество воздуха на df, потому что мы хотим попробовать нашу функцию с любым фреймом данных, а не только с качеством воздуха:

split_data <- function(df, train = TRUE){length<- nrow(df)total_row <- length *0.8split <- 1:total_rowif (train ==TRUE){train_df <- df[split, ]return(train_df)} else {test_df <- df[-split, ]return(test_df)}}

Давайте попробуем нашу функцию на наборе данных о качестве воздуха. у нас должен быть один набор со 122 строками и тестовый набор с 31 строкой.

train <- split_data(airquality, train = TRUE)dim(train)

Выход:

## [1] 122 6
test <- split_data(airquality, train = FALSE)dim(test)

Выход:

## [1] 31 6