2013-04-16 37 views
14

Có cấu trúc gói hoặc ngôn ngữ trong R tạo điều kiện hoặc cung cấp việc thực hiện "Python-like generators" không?Các chức năng của máy phát điện trong R

Bằng cách "phát Python-like" Ý tôi là chức năng mà giữ trạng thái giữa các cuộc gọi, trong cú pháp R và vay từ khóa năng suất từ Python sẽ được giống như:

iterable.fun <- function(){ 
    yield list('a','b','c') 
} 

Với năng suất thay vì một trở, sau đó gọi hàm ba lần liên tiếp sẽ cung cấp cho:

> iterable.fun() 
    'a' 
> iterable.fun() 
    'b' 
> iterable.fun() 
    'c' 

Edit: tôi rời ra một như pect của các trình tạo Python làm cho chúng khác với các trình lặp. Đó là toàn bộ danh sách các đối tượng để lặp lại không được xây dựng trên cuộc gọi đầu tiên và sau đó được lặp lại, nhưng mỗi lệnh gọi hàm tạo ra một phần tử sẽ trả về cho cuộc gọi đó.

+1

R cố gắng để trở thành một ngôn ngữ chức năng. Yêu cầu này chỉ có thể được thực hiện bằng cách tiếp cận phi chức năng. Bạn có thể phá hủy chức năng bằng '<< -' nếu cần thiết, nhưng có lẽ tốt hơn là bạn nên nghĩ về những gì bạn muốn làm kết quả cuối cùng, và tìm một giải pháp chức năng. –

+0

Câu hỏi tương tự: http://stackoverflow.com/questions/23509381/lazy-sequences-in-r – cbare

+0

Ngoài ra, Luke Tierney đã viết một [Lazy List Implementation] (http://homepage.cs.uiowa.edu/~ luke/R/lazy/lazy.pdf). – cbare

Trả lời

15

Gói iterators có chức năng này

library(iterators) 
abc <- iter(c('a','b','c')) 
nextElem(abc) 
## [1] "a" 
nextElem(abc) 
## [1] "b" 
nextElem(abc) 
## [1] "c" 

Hoặc bạn có thể sử dụng lambda.r<<-. Ví dụ này được sửa đổi từ

http://cartesianfaith.wordpress.com/2013/01/05/infinite-generators-in-r/

có nhiều ví dụ trong bài viết trên blog

library(lambda.r) 
seq.gen(start) %as% { 
    value <- start - 1L 
    function() { 
    value <<- value + 1L 
    return(value) 
    } 
} 



foo <- seq.gen(1) 
foo() 
## [1] 1 
foo() 
## [1] 2 
foo() 
## [1] 3 

lưu ý rằng bạn cũng có thể sử dụng một chức năng thường xuyên để làm điều này.

seq.gen <-function(start) { 
    value <- start - 1L 
    function() { 
    value <<- value + 1L 
    return(value) 
    } 
} 
foo2 <- seq.gen(1) 
foo2() 
## [1] 1 
foo2() 
## [1] 2 
foo2() 
## [1] 3 

Nếu bạn muốn chọn từ một danh sách có thể, sau đó bạn có thể làm như vậy có lẽ sử dụng switch

seq.char(start) %as% { 
    value <- start - 1L 
    function() { 
    value <<- value + 1L 
    return(switch(value,'a','b','c')) 
    } 
} 

foo.char <- seq.char(1) 
foo.char() 
## [1] "a" 
foo.char() 
## [1] "b" 
foo.char() 
## [1] "c" 
+0

Cảm ơn câu trả lời của bạn, thật không may một iterator không phải là những gì tôi đã nói về và tôi nghĩ rằng tôi đã không làm cho nó rõ ràng cho những người không quen thuộc với các chức năng máy phát điện Python. – papirrin

+0

@papirrin - xem chỉnh sửa của tôi. – mnel

+0

Chỉnh sửa đẹp, nó thậm chí còn trả lời những câu hỏi tôi không làm. – papirrin

Các vấn đề liên quan