1#![cfg_attr(not(feature = "std"), no_std)]
2
3#[cfg(feature = "std")]
4use std::{num::NonZeroUsize, ops::Range};
5
6#[cfg(not(feature = "std"))]
7use core::{num::NonZeroUsize, ops::Range};
8
9pub fn interleave<T: Copy, Vin: AsRef<[T]>, const CHANNELS: usize>(
39 input: &[Vin],
40 input_range: Range<usize>,
41 output: &mut [T],
42) {
43 assert!(CHANNELS > 0);
44 assert!(input.len() >= CHANNELS);
45
46 if input_range.is_empty() {
47 return;
48 }
49
50 assert!(output.len() >= (input_range.end - input_range.start) * CHANNELS);
51
52 for ch in input.iter() {
53 let ch = ch.as_ref();
54 assert!(input_range.start <= ch.len());
55 assert!(input_range.end <= ch.len());
56 }
57
58 unsafe {
60 interleave_unchecked::<T, _, CHANNELS>(input, input_range, output);
61 }
62}
63
64pub unsafe fn interleave_unchecked<T: Copy, Vin: AsRef<[T]>, const CHANNELS: usize>(
96 input: &[Vin],
97 input_range: Range<usize>,
98 output: &mut [T],
99) {
100 if input_range.is_empty() {
101 return;
102 }
103
104 unsafe {
105 for i in 0..(input_range.end - input_range.start) {
106 for ch_i in 0..CHANNELS {
107 *output.get_unchecked_mut((i * CHANNELS) + ch_i) = *input
108 .get_unchecked(ch_i)
109 .as_ref()
110 .get_unchecked(input_range.start + i);
111 }
112 }
113 }
114}
115
116pub fn deinterleave<T: Copy, Vout: AsMut<[T]>, const CHANNELS: usize>(
148 input: &[T],
149 output: &mut [Vout],
150 output_range: Range<usize>,
151) {
152 assert!(CHANNELS > 0);
153 assert!(output.len() >= CHANNELS);
154
155 if output_range.is_empty() {
156 return;
157 }
158
159 assert!(input.len() >= (output_range.end - output_range.start) * CHANNELS);
160
161 for ch in output.iter_mut() {
162 let ch = ch.as_mut();
163 assert!(output_range.start <= ch.len());
164 assert!(output_range.end <= ch.len());
165 }
166
167 unsafe {
169 deinterleave_unchecked::<T, _, CHANNELS>(input, output, output_range);
170 }
171}
172
173pub unsafe fn deinterleave_unchecked<T: Copy, Vout: AsMut<[T]>, const CHANNELS: usize>(
207 input: &[T],
208 output: &mut [Vout],
209 output_range: Range<usize>,
210) {
211 if output_range.is_empty() {
212 return;
213 }
214
215 unsafe {
216 for i in 0..(output_range.end - output_range.start) {
217 for ch_i in 0..CHANNELS {
218 *output
219 .get_unchecked_mut(ch_i)
220 .as_mut()
221 .get_unchecked_mut(output_range.start + i) =
222 *input.get_unchecked((i * CHANNELS) + ch_i)
223 }
224 }
225 }
226}
227
228pub fn interleave_variable<T: Copy, Vin: AsRef<[T]>>(
257 input: &[Vin],
258 input_range: Range<usize>,
259 output: &mut [T],
260 num_out_channels: NonZeroUsize,
261) {
262 if input_range.is_empty() || input.is_empty() {
263 return;
264 }
265
266 let in_frames = input_range.end - input_range.start;
267
268 if num_out_channels.get() == 1 {
269 output[..in_frames].copy_from_slice(&input[0].as_ref()[input_range.clone()]);
271
272 return;
273 }
274
275 if num_out_channels.get() == 2 && input.len() >= 2 {
276 interleave::<T, _, 2>(input, input_range, output);
278 return;
279 }
280
281 assert!(output.len() >= (input_range.end - input_range.start) * num_out_channels.get());
282
283 for (ch_i, in_ch) in (0..num_out_channels.get()).zip(input.iter()) {
284 let in_ch = in_ch.as_ref();
285
286 assert!(input_range.start < in_ch.len() && input_range.end <= in_ch.len());
287
288 unsafe {
291 for i in 0..(input_range.end - input_range.start) {
292 *output.get_unchecked_mut((i * num_out_channels.get()) + ch_i) =
293 *in_ch.get_unchecked(input_range.start + i);
294 }
295 }
296 }
297}
298
299pub fn deinterleave_variable<T: Copy, Vout: AsMut<[T]>>(
330 input: &[T],
331 num_in_channels: NonZeroUsize,
332 output: &mut [Vout],
333 output_range: Range<usize>,
334) {
335 if output_range.is_empty() || output.is_empty() {
336 return;
337 }
338
339 let out_frames = output_range.end - output_range.start;
340
341 if num_in_channels.get() == 1 {
342 output[0].as_mut()[output_range.clone()].copy_from_slice(&input[..out_frames]);
344
345 return;
346 }
347
348 if num_in_channels.get() == 2 && output.len() >= 2 {
349 deinterleave::<T, _, 2>(input, output, output_range);
351 return;
352 }
353
354 assert!(input.len() >= (output_range.end - output_range.start) * num_in_channels.get());
355
356 for (ch_i, out_ch) in (0..num_in_channels.get()).zip(output.iter_mut()) {
357 let out_ch = out_ch.as_mut();
358
359 assert!(output_range.start < out_ch.len() && output_range.end <= out_ch.len());
360
361 unsafe {
364 for i in 0..(output_range.end - output_range.start) {
365 *out_ch.get_unchecked_mut(output_range.start + i) =
366 *input.get_unchecked((i * num_in_channels.get()) + ch_i);
367 }
368 }
369 }
370}
371
372#[cfg(test)]
373mod tests {
374 use super::*;
375
376 #[test]
377 fn test_interleave() {
378 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4]];
379 let mut output: Vec<i32> = vec![0; 4];
380 interleave::<_, _, 1>(&input, 1..4, &mut output);
381 assert_eq!(&output, &[2, 3, 4, 0]);
382
383 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4], vec![5, 6, 7, 8]];
384 let mut output: Vec<i32> = vec![0; 8];
385 interleave::<_, _, 2>(&input, 1..4, &mut output);
386 assert_eq!(&output, &[2, 6, 3, 7, 4, 8, 0, 0]);
387
388 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4], vec![5, 6, 7, 8], vec![9, 10, 11, 12]];
389 let mut output: Vec<i32> = vec![0; 12];
390 interleave::<_, _, 3>(&input, 1..4, &mut output);
391 assert_eq!(&output, &[2, 6, 10, 3, 7, 11, 4, 8, 12, 0, 0, 0]);
392 }
393
394 #[test]
395 fn test_deinterleave() {
396 let input: Vec<i32> = vec![1, 2, 3, 4];
397 let mut output: Vec<Vec<i32>> = vec![vec![0; 4]];
398 deinterleave::<_, _, 1>(&input, &mut output, 1..4);
399 assert_eq!(&output[0], &[0, 1, 2, 3]);
400
401 let input: Vec<i32> = vec![1, 2, 3, 4, 5, 6, 7, 8];
402 let mut output: Vec<Vec<i32>> = vec![vec![0; 4], vec![0; 4]];
403 deinterleave::<_, _, 2>(&input, &mut output, 1..4);
404 assert_eq!(&output[0], &[0, 1, 3, 5]);
405 assert_eq!(&output[1], &[0, 2, 4, 6]);
406
407 let input: Vec<i32> = vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
408 let mut output: Vec<Vec<i32>> = vec![vec![0; 4], vec![0; 4], vec![0; 4]];
409 deinterleave::<_, _, 3>(&input, &mut output, 1..4);
410 assert_eq!(&output[0], &[0, 1, 4, 7]);
411 assert_eq!(&output[1], &[0, 2, 5, 8]);
412 assert_eq!(&output[2], &[0, 3, 6, 9]);
413 }
414
415 #[test]
416 fn test_interleave_variable() {
417 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4]];
418 let mut output: Vec<i32> = vec![0; 4];
419 interleave_variable(&input, 1..4, &mut output, NonZeroUsize::new(1).unwrap());
420 assert_eq!(&output, &[2, 3, 4, 0]);
421
422 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4], vec![5, 6, 7, 8]];
423 let mut output: Vec<i32> = vec![0; 8];
424 interleave_variable(&input, 0..4, &mut output, NonZeroUsize::new(1).unwrap());
425 assert_eq!(&output, &[1, 2, 3, 4, 0, 0, 0, 0]);
426
427 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4]];
428 let mut output: Vec<i32> = vec![0; 8];
429 interleave_variable(&input, 0..4, &mut output, NonZeroUsize::new(2).unwrap());
430 assert_eq!(&output, &[1, 0, 2, 0, 3, 0, 4, 0]);
431
432 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4], vec![5, 6, 7, 8]];
433 let mut output: Vec<i32> = vec![0; 8];
434 interleave_variable(&input, 0..4, &mut output, NonZeroUsize::new(2).unwrap());
435 assert_eq!(&output, &[1, 5, 2, 6, 3, 7, 4, 8]);
436
437 let input: Vec<Vec<i32>> = vec![vec![1, 2, 3, 4], vec![5, 6, 7, 8], vec![9, 10, 11, 12]];
438 let mut output: Vec<i32> = vec![0; 12];
439 interleave_variable(&input, 0..4, &mut output, NonZeroUsize::new(3).unwrap());
440 assert_eq!(&output, &[1, 5, 9, 2, 6, 10, 3, 7, 11, 4, 8, 12]);
441 }
442
443 #[test]
444 fn test_deinterleave_variable() {
445 let input: Vec<i32> = vec![1, 2, 3, 4];
446 let mut output: Vec<Vec<i32>> = vec![vec![0; 4]];
447 deinterleave_variable(&input, NonZeroUsize::new(1).unwrap(), &mut output, 1..4);
448 assert_eq!(&output[0], &[0, 1, 2, 3]);
449
450 let input: Vec<i32> = vec![1, 2, 3, 4];
451 let mut output: Vec<Vec<i32>> = vec![vec![0; 4], vec![0; 4]];
452 deinterleave_variable(&input, NonZeroUsize::new(1).unwrap(), &mut output, 0..4);
453 assert_eq!(&output[0], &[1, 2, 3, 4]);
454 assert_eq!(&output[1], &[0, 0, 0, 0]);
455
456 let input: Vec<i32> = vec![1, 2, 3, 4, 5, 6, 7, 8];
457 let mut output: Vec<Vec<i32>> = vec![vec![0; 4]];
458 deinterleave_variable(&input, NonZeroUsize::new(2).unwrap(), &mut output, 0..4);
459 assert_eq!(&output[0], &[1, 3, 5, 7]);
460
461 let input: Vec<i32> = vec![1, 2, 3, 4, 5, 6, 7, 8];
462 let mut output: Vec<Vec<i32>> = vec![vec![0; 4], vec![0; 4]];
463 deinterleave_variable(&input, NonZeroUsize::new(2).unwrap(), &mut output, 0..4);
464 assert_eq!(&output[0], &[1, 3, 5, 7]);
465 assert_eq!(&output[1], &[2, 4, 6, 8]);
466
467 let input: Vec<i32> = vec![1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
468 let mut output: Vec<Vec<i32>> = vec![vec![0; 4], vec![0; 4], vec![0; 4]];
469 deinterleave_variable(&input, NonZeroUsize::new(3).unwrap(), &mut output, 0..4);
470 assert_eq!(&output[0], &[1, 4, 7, 10]);
471 assert_eq!(&output[1], &[2, 5, 8, 11]);
472 assert_eq!(&output[2], &[3, 6, 9, 12]);
473 }
474}