2017-05-18 3 views
0

Ich versuche, eine R-Funktion zu erstellen, die die Tage Miete in einem Monat berechnen kann. Es hätte als Argumente: start_date, end_date, aktueller Monat. Und eine ganzzahlige Ausgabe von Miettagen im Monat zurückgeben. (Dies wird im Zusammenhang mit einem Apartment-Mietmodell verwendet).Miete Tage im Monat Funktion

Zum Beispiel

library(lubridate) 

start_date <- ymd('2017-06-15') 
end_date <- ymd('2018-06-14') 
current_month <- ymd('2017-06-01') 

rent_days_in_month(start_date, end_date, current_month) 
[1] 16 

Ich habe eine Funktion, die ich Werke denken, aber es scheint zu kompliziert. Ich möchte auch sicherstellen, dass dies vektorisiert funktioniert, so dass ich auf einen Datenrahmen mit mutate anwenden kann.

Hier ist meine Funktion:

rent_days_in_month <- function(start_date, 
           end_date, 
           current_month){ 

    last_day_in_month <- ceiling_date(current_month, 
            unit = "months") - 1 

    current_month_days_in_moth <- days_in_month(current_month) 

    first_day_in_month <- floor_date(current_month, 
            unit = "month") 

    if (last_day_in_month < start_date) { 

    rent_days_in_month <- 0 

    return(rent_days_in_month) 

    } 

    rent_days_in_month <- as.numeric(end_date - start_date + 1) 

    rent_days_in_month <- min(rent_days_in_month, 
          current_month_days_in_moth) 


    if (end_date < last_day_in_month){ 

    if (end_date > first_day_in_month){ 

     if (start_date > first_day_in_month) { 

     rent_days_in_month <- end_date - start_date - 1 

     return(rent_days_in_month) 

     } else { 

     rent_days_in_month <- end_date - first_day_in_month 

     return(rent_days_in_month) 
     } 

    } else { 

     rent_days_in_month <- 0 

     return(rent_days_in_month) 

    } 

    } 

    return(rent_days_in_month) 

} 

Ich habe dann versucht, um es dies zu machen vektorisiert mag:

v_rent_days_in_month <- Vectorize(rent_days_in_month) 

Gibt es irgendetwas gibt, das würde als dies einfacher arbeiten? Außerdem möchte ich wissen, ob dies die richtige Verwendung der Vectorize-Funktion ist.

Dank

+0

Können Sie erklären, was Ihre Funktion macht? Ich sehe nicht, wie du in deinem Beispiel zu "16" gekommen bist. –

+0

Die Funktion, die Sie mit den von Ihnen angegebenen Argumenten geschrieben haben, spuckte "30" und nicht "16" aus! –

+0

Danke Yannis, du hast Recht! Meine Funktion funktioniert nicht. Es sollte ein Lease-Startdatum, ein Lease-Enddatum und einen Monat zur Auswertung verwendet werden. Dann soll es die geltenden Miettage zurückgeben, die berechnet werden. Es sollte 16 sein, nicht 30. –

Antwort

0
library(lubridate) 
start_date <- as.Date("2017-06-15") 
end_date <- as.Date("2018-06-14") 
current_month<- as.Date("2017-06-01") 

rent_days_in_month = function(start_date, end_date, current_month){ 
    if(month(current_month) == month(start_date) & year(current_month) == year(start_date)){ 
    return(as.numeric(difftime(ceiling_date(start_date, "month"), start_date, units = c("days")))) 
    }else if(current_month < floor_date(start_date, "month") | current_month >= ceiling_date(end_date)){ 
    return("invalid date") 
    }else if(month(current_month) == month(end_date) & year(current_month) == year(end_date)){ 
    return(as.numeric(difftime(end_date, current_month, units = c("days"))) + 1) 
    }else{ 
    tmp = ceiling_date(current_month, "month") - 1 
    return(day(tmp)) 
    } 

} 

> rent_days_in_month(start_date, end_date, current_month) 
[1] 16 

> rent_days_in_month(start_date, end_date, as.Date("2015-01-01")) 
[1] "invalid date" 

> rent_days_in_month(start_date, end_date, as.Date("2018-01-01")) 
[1] 31 

> rent_days_in_month(start_date, end_date, as.Date("2018-06-01")) 
[1] 14 
+0

Kristoferson, danke. Das scheint genau so zu funktionieren, wie ich es versuche! Denkst du auch, würde mit mutate auf einem data.frame arbeiten. Danke noch einmal! –

+0

@ChrisKiniry Ich habe ehrlich gesagt nie mutiert. Ich habe mir aber die Hilfe-Datei angeschaut und kann nicht sehen, warum das nicht funktioniert. Geben Sie eine Chance und melden Sie es zurück, wenn es fehlschlägt. – Kristofersen

+0

Es scheint auf einem data.frame mit mutate zu funktionieren, wenn ich Folgendes tue: v_rent_days_in_month <- Vectorize (rent_days_in_month) –

0
library(lubridate) 
start_date <- as.Date('2017-06-15') 
end_date <- as.Date('2018-06-14') 
days <- seq(start_date, end_date, by= 'days') 
lapply(split(days, month(days)), length) 

Verwenden Sie die seq Funktion mit dem Argument = 'Tage' einen Vektor von all jenen Tagen zu erhalten. Dann in eine Liste nach Monat und Summe aufteilen.

Verwandte Themen