MCPcopy Create free account
hub / github.com/MoonInTheRiver/DiffSinger / _f02sine

Method _f02sine

modules/parallel_wavegan/models/source.py:44–102  ·  view source on GitHub ↗

f0_values: (batchsize, length, dim) where dim indicates fundamental tone and overtones

(self, f0_values)

Source from the content-addressed store, hash-verified

42 return uv
43
44 def _f02sine(self, f0_values):
45 """ f0_values: (batchsize, length, dim)
46 where dim indicates fundamental tone and overtones
47 """
48 # convert to F0 in rad. The interger part n can be ignored
49 # because 2 * np.pi * n doesn't affect phase
50 rad_values = (f0_values / self.sampling_rate) % 1
51
52 # initial phase noise (no noise for fundamental component)
53 rand_ini = torch.rand(f0_values.shape[0], f0_values.shape[2], \
54 device=f0_values.device)
55 rand_ini[:, 0] = 0
56 rad_values[:, 0, :] = rad_values[:, 0, :] + rand_ini
57
58 # instantanouse phase sine[t] = sin(2*pi \sum_i=1 ^{t} rad)
59 if not self.flag_for_pulse:
60 # for normal case
61
62 # To prevent torch.cumsum numerical overflow,
63 # it is necessary to add -1 whenever \sum_k=1^n rad_value_k > 1.
64 # Buffer tmp_over_one_idx indicates the time step to add -1.
65 # This will not change F0 of sine because (x-1) * 2*pi = x * 2*pi
66 tmp_over_one = torch.cumsum(rad_values, 1) % 1
67 tmp_over_one_idx = (tmp_over_one[:, 1:, :] -
68 tmp_over_one[:, :-1, :]) < 0
69 cumsum_shift = torch.zeros_like(rad_values)
70 cumsum_shift[:, 1:, :] = tmp_over_one_idx * -1.0
71
72 sines = torch.sin(torch.cumsum(rad_values + cumsum_shift, dim=1)
73 * 2 * np.pi)
74 else:
75 # If necessary, make sure that the first time step of every
76 # voiced segments is sin(pi) or cos(0)
77 # This is used for pulse-train generation
78
79 # identify the last time step in unvoiced segments
80 uv = self._f02uv(f0_values)
81 uv_1 = torch.roll(uv, shifts=-1, dims=1)
82 uv_1[:, -1, :] = 1
83 u_loc = (uv < 1) * (uv_1 > 0)
84
85 # get the instantanouse phase
86 tmp_cumsum = torch.cumsum(rad_values, dim=1)
87 # different batch needs to be processed differently
88 for idx in range(f0_values.shape[0]):
89 temp_sum = tmp_cumsum[idx, u_loc[idx, :, 0], :]
90 temp_sum[1:, :] = temp_sum[1:, :] - temp_sum[0:-1, :]
91 # stores the accumulation of i.phase within
92 # each voiced segments
93 tmp_cumsum[idx, :, :] = 0
94 tmp_cumsum[idx, u_loc[idx, :, 0], :] = temp_sum
95
96 # rad_values - tmp_cumsum: remove the accumulation of i.phase
97 # within the previous voiced segment.
98 i_phase = torch.cumsum(rad_values - tmp_cumsum, dim=1)
99
100 # get the sines
101 sines = torch.cos(i_phase * 2 * np.pi)

Callers 1

forwardMethod · 0.95

Calls 1

_f02uvMethod · 0.95

Tested by

no test coverage detected