R을 사용하여 생일 음악을 재생하려면 어떻게해야합니까? [닫은]


80

R을 사용하여 음악을 재생하고 싶습니다. R이이 목적에 가장 적합한 도구는 아니지만, 제가 익숙한 도구이며, 이러한 즐거운 기회에 다른 사람들에게 유연성을 보여 주면 좋을 것입니다.

이것을 어떻게 할 수 있습니까?


7
R을 통해 BD 음악을 재생하려는 이유는 무엇입니까? R은 통계 프로그래밍 언어입니다. 이러한 작업을위한 더 나은 플랫폼이있을 것입니다.
David Arenburg

13
@DavidArenburg는 확실히 사실입니다. 그러나이 파일 tinyurl.com/odlurth의 33 페이지를보십시오 (폴 머렐의 "R Graphics"). 무언가를하기위한 더 나은 프로그램이 있다는 사실이 우리가 Feng Tian을 도우려는 것을 방해해서는 안됩니다 (아마도 그 과정에서 새로운 무언가)
MaZe

11
IMHO, 그 질문에 약간의 장점이있을 수 있습니다. 소리 분석 ( 2 )은 합법적 인 분석 작업이므로 분석 작업을 수행하는 동안 소리 샘플을 조직적으로 확인하려는 상황을 상상할 수 있습니다. 그래도 제목 의 생일 음악 은 다소 이상합니다.
Konrad

8
질문 할 가능성이 있으므로 이러한 종류의 질문을 권장하지 마십시오 I would like to play video using R.
Avinash Raj

7
@AvinashRaj 흥미롭게도 나는 그것을 후속 조치로 생각했습니다 :) 모든 진지함에서 옵션은 사소한 것 (외부 프로그램 시작), 무의미한 (외부 코드에서 비디오 플레이어 다시 구현) 또는 사용할 수없는 (R 코드 사용) 비디오 스트림 디코딩 및 rasterImage각 프레임 렌더링)
Nick Kennedy

답변:


237

정말로 이것을하고 싶다면 :

library("audio")

bday_file <- tempfile()
download.file("http://www.happybirthdaymusic.info/01_happy_birthday_song.wav", bday_file, mode = "wb")
bday <- load.wave(bday_file)
play(bday)

install.packages("audio")먼저 해야합니다 . 특정 파일이 이미있는 경우 먼저 WAV 형식으로 변환해야합니다.

WAV 파일을 재생하는 것보다 더 많은 프로그램을 원하신다면, 일련의 사인파에서 곡을 생성하는 버전이 있습니다.

library("dplyr")
library("audio")
notes <- c(A = 0, B = 2, C = 3, D = 5, E = 7, F = 8, G = 10)
pitch <- "D D E D G F# D D E D A G D D D5 B G F# E C5 C5 B G A G"
duration <- c(rep(c(0.75, 0.25, 1, 1, 1, 2), 2),
              0.75, 0.25, 1, 1, 1, 1, 1, 0.75, 0.25, 1, 1, 1, 2)
bday <- data_frame(pitch = strsplit(pitch, " ")[[1]],
                   duration = duration)

bday <-
  bday %>%
  mutate(octave = substring(pitch, nchar(pitch)) %>%
           {suppressWarnings(as.numeric(.))} %>%
           ifelse(is.na(.), 4, .),
         note = notes[substr(pitch, 1, 1)],
         note = note + grepl("#", pitch) -
           grepl("b", pitch) + octave * 12 +
           12 * (note < 3),
         freq = 2 ^ ((note - 60) / 12) * 440)

tempo <- 120
sample_rate <- 44100

make_sine <- function(freq, duration) {
  wave <- sin(seq(0, duration / tempo * 60, 1 / sample_rate) *
                freq * 2 * pi)
  fade <- seq(0, 1, 50 / sample_rate)
  wave * c(fade, rep(1, length(wave) - 2 * length(fade)), rev(fade))
}

bday_wave <-
  mapply(make_sine, bday$freq, bday$duration) %>%
  do.call("c", .)

play(bday_wave)

주의해야 할 몇 가지 사항이 있습니다. 음표의 기본 옥타브는 옥타브 4이며 A4는 440Hz (오케스트라를 튜닝하는 데 사용되는 음표)입니다. 옥타브는 C에서 전환되므로 C3은 B2보다 한 반음 높습니다. 페이드 인 make_sine이없는 이유는 음표를 시작하고 중지 할 때 팝이 들리기 때문입니다.


6
@DavidArenburg 감사합니다. 그냥 약간 더 말도 안되는 일을하기 위해, 지금 : 사인파를 사용하여 첫 번째 원칙에서 조정을 생성하는 코드 추가 한
닉 케네디

멋진 대답입니다. 나는 새로운 것을 배웠습니다. 나는 페이딩에 대해 몰랐고, 최근 제 실험에이 정확한 문제가있었습니다. Nitpick : 인용 할 아무 이유 c에서 do.call, 그리고 마지막 할당은 make_sine필요하지 않습니다.
Konrad Rudolph

1
@KonradRudolph 감사합니다. 나는 항상 함수 이름을 do.call. a <- 1; b <- 2; c <- 3길을 따라와 같은 일을 한 덫에 빠지는 것은 너무나 쉽다 . 그리고 그 상황에서는 do.call(c, ...)실패하지만 c(1, 2, 3)그렇지 않을 것이다. 그러나 후자의 요점에 완전히 동의하고 불필요한 할당을 제거했습니다!
Nick Kennedy

1
@KonradRudolph 실제로 do.call("c", ...)작동합니다. 시도해보십시오 c <- 4; do.call("c", list(1, 2)). R은 대부분의 경우 함수를 받아들이는 인수가 함수 자체 또는 함수 이름을 받아 들인다는 점에서 합리적으로 일관성이 있습니다. 어떤 경우에 (예 lapply),이 경유 match.fun등 다른에서 반면 do.call, getMethod상기 구현은 (a 호출을 통해 후자에 대한 C 코드이다 C_R_getGeneric). 왜 스타일 적으로 이름보다는 함수를 전달하는 것을 선호하는지 알 수 있지만 후자의 동작은 잘 문서화되어 있습니다.
Nick Kennedy

2
@KonradRudolph 충분합니다. 관련 문제는 a 가 괄호 뒤에 오면 R이 항상 함수를 찾는다는 것 입니다. 이렇게하면 기본을 사용하지 않고 정상적으로 작동 할 수 있습니다 . 나는 누군가가 자신의 코드를 매우 즐겁게 호출 했지만 작동하지 않는 혼란을 보았습니다 . 하루가 끝나면 기능이 이름으로 제공되는지 직접 제공되는지에 대해 강하게 느끼지 않습니다. symbolsymbolc <- 4; c(1, 2)c <- paste0; c(1, 2)cc(1, 2)do.call(c, ...)
Nick Kennedy
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.