-
Notifications
You must be signed in to change notification settings - Fork 1
/
NVI_calculation_warbleR_1.0.R
143 lines (106 loc) · 5.92 KB
/
NVI_calculation_warbleR_1.0.R
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
#This program calculates the song complexity using Note Variability Index (NVI) (Sawant S., Arvind C., Joshi V., Robin V. V., 2021)
#This program uses warbleR to calculate Spectrogram Cross-Correlation
#Input files: Raven selection table for notes with sound files in same directory
#The notes selection table should include- Begin Time (s), End Time (s), Low Frequency (Hz), High Frequency (Hz),
# Begin File, File Offset (s), Song No..
#-------------------------------------------------------------------------------------------------------------------------------
#This part generates cross-correlation table from the Raven Notes selection table
library(Rraven)
#set working directory
#setwd('PATH')
#import raven note selection table with sound files in same directory
Notes_for_Corr <- imp_raven(warbler.format = TRUE)
#set windows length
wl <- 512
#set time window overlap
ovlp <- 50
#frequency limits based on the low and high frequencies in the note selection table
bp <- c(min(Notes_for_Corr$bottom.freq)-0.1, max(Notes_for_Corr$top.freq)+0.1)
#run batch correlator on all the selections in note selection table
#set any correlation method- pearson, spearman or kendall
batch_corr_output <- xcorr(Notes_for_Corr, bp = bp, cor.method = "pearson" )
#convert negative correlation to no correlation
nonneg_batch_corr_output <- pmax(batch_corr_output,0)
BatchCorrOutput <- nonneg_batch_corr_output
#-------------------------------------------------------------------------------------------------------------------------------
#This part creates Raven Songs selection table from the Notes Selections
library("readr")
#Import raven selection table for notes in the txt form
#with an annotation column- 'Song No.'
#for alloting each note under some song
Notes_Selections <-as.data.frame(read_tsv("BRTH_notes_selections.txt", col_names = T))
#Extract Unique song IDs
Unique_Songs <- as.data.frame(unique(Notes_Selections$`Song No.`))
#No. of Songs
Total_songs <- length(unique(Notes_Selections$`Song No.`))
#Create data frame for songs selection table
Song_Selections <- data.frame(matrix(nrow = Total_songs, ncol = ncol(Notes_Selections)))
colnames(Song_Selections) <- names(Notes_Selections)
colnames(Song_Selections)[ncol(Song_Selections)] <- "Note Count"
#Create selection table for songs
Song_Selections[,1] <- c(1:Total_songs)
Song_Selections[,2] <- "Spectrogram 1"
Song_Selections[,3] <- 1
Begin_Time <- aggregate(Notes_Selections$`Begin Time (s)` , by = list(Category = Notes_Selections$`Song No.`), FUN = min)
Song_Selections[,4] <- Begin_Time$x
End_Time <- aggregate(Notes_Selections$`End Time (s)` , by = list(Category = Notes_Selections$`Song No.`), FUN = max)
Song_Selections[,5] <- End_Time$x
Min_Freq <- aggregate(Notes_Selections$`Low Freq (Hz)` , by = list(Category = Notes_Selections$`Song No.`), FUN = min)
Song_Selections[,6] <- Min_Freq$x
Max_Freq <- aggregate(Notes_Selections$`High Freq (Hz)` , by = list(Category = Notes_Selections$`Song No.`), FUN = max)
Song_Selections[,7] <- Max_Freq$x
Note_Count <- aggregate(Notes_Selections$Channel , by = list(Category = Notes_Selections$`Song No.`), FUN = sum )
Song_Selections[,ncol(Song_Selections)] <- Note_Count$x
#-------------------------------------------------------------------------------------------------------------------------------
#This part calculates the song complexity values using Note Variability INdex(NVI)
######### NVI calculation from Batch Correlator Output #########
### ## ## ## ####
#### ## ## ## ##
## ## ## ## ## ##
## #### #### ##
## ### ## ####
#extract song lengths from the songs selction table
SongLength <- as.data.frame(Song_Selections$`Note Count`)
#Create datasheet for the start and end of each song
start_end <- data.frame(matrix(nrow = nrow(SongLength), ncol = 2))
start_end <- cbind(SongLength,start_end)
colnames(start_end) <- c("Note_Count","Start_note", "end_note")
for (i in 2:nrow(start_end)){
start_end[1,2] <- 1
start_end[1,3] <- start_end[1,1]
start_end[i,2] <- 1 + start_end[i-1,3]
start_end[i,3] <- start_end[i,1] + start_end[i-1,3]
}
#Extract total number of notes to be correlated from the individual note count of songs
Total_notes <- start_end[nrow(start_end),3]
#Extract note count, start note and end note fpr each song
StartNote <- start_end$Start_note
EndNote <- start_end$end_note
NoteCount <- start_end$Note_Count
#creat output dataframe for NVI values
NVI_output <- data.frame(matrix(nrow = nrow(SongLength), ncol = 3))
colnames(NVI_output) <- c("No. of notes","NVI_non_norm", "NVI")
#Calculate the NVI values based on the song bounds provided
for (x in 1:nrow(SongLength)){
i = StartNote[c(x)]
j = EndNote[c(x)]
k = NoteCount[c(x)]
NVI_non_norm <-sum((1-BatchCorrOutput[c(i:j),c(i:j)]))
NVI <-sum((1-BatchCorrOutput[c(i:j),c(i:j)]))/(k*(k-1))
NVI_output[x, 1] <- k
NVI_output[x, 2] <- NVI_non_norm
NVI_output[x, 3] <- NVI
}
#add NVI values to raven selection table
NVI <- NVI_output$NVI
Song_Selections_Output <- cbind(Song_Selections, NVI)
#remove objects
rm("SongLength","BatchCorrOutput","StartNote","EndNote","NoteCount","start_end",
"Song_Selections", "i","j","k","x", "NVI", "NVI_non_norm", "bp", "ovlp", "wl",
"Begin_Time","End_Time","Max_Freq","Min_Freq","Note_Count","Unique_Songs",
"batch_corr_output","nonneg_batch_corr_output")
#Write Raven selection table for songs with added NVI values in txt format
write.table(Song_Selections_Output, file = "Song_Selections_Output.txt", sep = "\t", quote = F,row.names = FALSE)
#Export NVI output as a csv file
#write.csv(NVI_output, "NVI_Output.csv")
#_______________________________________________________________________________________________________________________________