2017-07-17 86 views
1

我有一個文件夾中的氣候文件列表(EDU鏈接:https://cloudstor.aarnet.edu.au/plus/index.php/s/QFpaBDR7q2GbDCN)。他們被命名爲如下p[year][month]_0p5.asc創建一系列文件副本並重命名它們

例子:

p198001_0p5.asc 

p198002_0p5.asc 

... 

p198012_0p5.asc 

p198101_0p5.asc 

... 

p201012_0p5.asc 

我希望通過這個順序重複這31年(1980至2010年),並重新命名他們有從p198001_0p5.asc文件的列表p397912_0p5.asc

創建2000年數據

例如,最終文件夾將包含p201101_0p5.asc,其中包含與p198001_0p5.asc相同的數據,但將被命名爲p201101_0p5.asc

我不知道如何在R中做到這一點。任何幫助將不勝感激!

更新19-07-2017:@ Mako212建議似乎工作,但我有內存問題(錯誤消息#保護():保護堆棧溢出)。我改變了我的策略,並根據他的建議創建了另一個腳本,從1880年到2010年創造了131年的數據。我通過重複31年(1980-2010)的系列來做到這一點。如果您希望查看該策略,則可以使用代碼。它工作正常:

require(purrr) 
require(data.table) 
library(raster) 

setwd('...') 
files <- list.files(pattern= "*.asc") 
files 
length(files) 

fileDF <- files %>% map(raster) 

#set the output directory 
output_dir <- "..." 

# set month and year counters 
startYear <- 2010 
startMonth <- 12 
fileNumber <- 1 

for (i in fileDF){ 
    startYear <- 2010 - (fileNumber-1) %/% 12 
    for (x in 1:6){ 
    print(startYear) 
    print(startMonth) 
    print(fileNumber) 
    writeRaster(i, paste(output_dir, sprintf("p%d%s%d_0p5.asc", startYear, ifelse(startMonth<10,0,""), startMonth), sep="/"), format = "ascii") 
    startYear <- startYear - 31 
    if (startYear < 1880) break # don't create files before December, 1880 
    } 
    if (startMonth > 1) { 
    startMonth <- startMonth - 1 
    } 
    else{ 
    startMonth <- 12 
    } 
    fileNumber <- fileNumber + 1  
} 
+1

我想你可以通過嵌套的for循環來實現。你需要'list.files(pattern =「* .asc」)'。然後,沿着'for(f in files){for(x in 1:65){write.csv(f,sprintf(「p%d」,x))}}'這行代碼。構建完整的文件名需要多一點技巧,但這是總體思路。 – Mako212

回答

1

好了,這裏的總體思路:

require(purrr) 
require(data.table) 
# after playing with SDMTools::read.asc, data.table::fread seems to 
# be more reliable. That said, if fread() isn't reading your data 
# correctly, you might try using the SDMTools function instead. 
# I also chose to save everything as .csv, but again, you can try 
# using the SDMTools read/write.asc functions if you want 

files <- list.files(pattern= "*.asc") 


fileDF <- files %>% map(fread) 

# set month and year counters 

startYear <- 1980 
startMonth <- 1 
fileNumber <- 1 

for (i in fileDF){ 


    # increment startYear by 1 every 13th file 
    startYear <- 1980 + (fileNumber-1) %/% 12 

    for (x in 1:65){ 
     # added underscore for clarity between year and month 
     # format is p1980_01_0p5.csv 
     write.csv(i, sprintf("p%d_%s%d_0p5.csv", startYear, ifelse(startMonth<10,0,""), startMonth)) 
     startYear <- startYear + 31 

     # don't create files past December, 3979 
     if (startYear > 3979) break 
    } 
    if (startMonth < 12) { 
     startMonth <- startMonth +1 
    } 
    else{ 
     startMonth <- 1 
    } 

    fileNumber <- fileNumber + 1  


} 

循環計數器設定假設你有有價值的數據(12名* 31的文件)

製作的正是31年當然,你寫入一個新的文件夾(不是包含源數據的文件夾)

+0

非常感謝你!我在代碼中使用了'fileDF <- files %>%map(raster)'和'writeRaster'。 1980年,2011年,2042 ... 3964(31年增量)的所有12個月都被正確保存,但隨後循環返回到1980年1月文件編號13,因此我有一個文件覆蓋問題。我已經添加了一個31 * 12 .asc文件的樣本(EDU鏈接) – Cecile

+0

@Cecile你可以發佈你現在運行的代碼嗎?聽起來好像有可能在某處出現錯字。如果循環運行正確,'fileNumber'永遠不會關閉。循環應該結束並且'fileNumber'應該等於372 – Mako212

+0

@Cecile在此期間我正在下載您的示例數據以查看我是否可以找到任何問題 – Mako212

相關問題