Python3 Course Removing Vocals: Code problem solving in Python

User Generated

Gerfbznorpx

Writing

Description

Problems

Problem 1: Removing Vocals

Listen to the wav file with vocals (love.wav) in your repository folder. (Note: You can play WAV files in Windows Media Player (Windows 10) or iTunes (macOS) after you download them. You'll also find it convenient to play sounds from within Python itself.)

The function you write for this problem, remove_vocals will be able to take a sound object created from that file, and produce a new sound object that is the same as the original sound but with vocals removed. The header for this function is given below.

def remove_vocals(snd):

The remove_vocals function takes a sound object snd as a parameter, and creates and returns a new sound with vocals removed using the algorithm described below. The new sound has the same number of samples as snd. (Remember: The original sound, snd, should NOT be modified.)

The algorithm works as follows. Any given sample in snd contains two integer values, one for the left channel and one for the right. Call these values left and right. For each sample in snd, compute (left - right) / 2, and use this value for both the left and right channels of the corresponding sample in the new sound you are creating.

Here's an example. Let's say that snd contains the following three samples, each composed of two values:

  • (1010, 80)
  • (1500, -4200)
  • (-65, 28132)

Your program will produce a new sound consisting of the following three samples:

  • (465, 465)
  • (2850, 2850)
  • (-14098, -14098)

If you do the math, you'll notice that the values in the third sample should have both been the fractional number -14098.5; but sample values must be integers. Make sure you use the "floor division" operator in (i.e. "//") to produce an integer rather than a floating point number. Keep this in mind for all of the functions you write in this assignment.

Example Usage

Below is a short bit of Python code that shows how you could use the function you just wrote. This code is written assuming you are using the Python REPL, which you started while in your repository directory.

import sound
import comp110_psa2

love = sound.Sound("love.wav")
love.play()
love_no_vocals = comp110_psa2.remove_vocals(love)
love.stop()
love_no_vocals.play()

Why This Algorithm Works

For the curious, a brief explanation of the vocal-removal algorithm is in order. As you noticed from the algorithm, we are simply subtracting one channel from the other and then dividing by 2 (to keep the volume from getting too loud). So why does subtracting the right channel from the left channel magically remove vocals?

When music is recorded, it is sometimes the case that vocals are recorded by a single microphone, and that single vocal track is used for the vocals in both channels. The other instruments in the song are recorded by multiple microphones, so that they sound different in both channels. Subtracting one channel from the other takes away everything that is "in common" between those two channels which, if we're lucky, means removing the vocals.

Of course, things rarely work so well. Try your vocal remover on this badly-behaved wav file (cartoon.wav). Sure, the vocals are gone, but so is the body of the music! Apparently some of the instruments were also recorded "centred," so that they are removed along with the vocals when channels are subtracted. When you're tired of that one, try this harmonized song (harmony.wav). Can you hear the difference once you remove the vocals? Part of the harmony is gone!

Grading remove_vocals

The remove_vocals function is worth <#points 7 pts>, broken down as follows.

  • Vocals correctly removed using specified algorithm. <#points 3 pts>
  • Effect works on all samples in sound. <#points 1 pts>
  • Original sound not modified. <#points 2 pts>
  • Correct docstring comment at beginning of function and appropriate comments in the body of the function. <#points 1 pt>

Problem 2: Fading In and Out

For this problem, you will be writing three functions that will produce fade-in and fade-out effects. As with Problem 1, these functions should not modify the original sound object: they should create a copy of that original, modify the copy, then return that copy.

Fade-in

Start this problem by implementing the fade_in function, whose function header is given below.

def fade_in(snd, fade_length):

This function takes a sound object and an integer indicating the number of samples to which the fade-in will be applied. For example, if fade_length is 88200, the fade-in should not affect any sample numbered 88200 or higher. (Reminder: The first sample in a sound is numbered 0.)

Before we discuss how to accomplish fade-in, let's get acquainted with some fading-in. Listen to this monotonous sound of water bubbling (waver.wav). The volume is stable throughout. Now, with the call fade_in(water, 88200) (where water is a sound object loaded with the water sound), we get water with a short fade-in. Notice how the water linearly fades in over the first two seconds, then remains at maximum volume throughout. (88200 corresponds to two seconds, because we're using sounds recorded at 44100 samples per second.) Finally, with the call fade_in(water, len(water)), we get water with a long fade-in. The fade-in is slowly and linearly applied over the entire duration of the sound, so that the maximum volume is reached only at the very last sample.

To apply a fade-in to a sound, we multiply successive samples by larger and larger fractional numbers between 0 and 1. Multiplying samples by 0 silences them, and multiplying by 1 (obviously) keeps them the same. Importantly, multiplying by a factor between 0 and 1 scales their volume by that factor.

Here's an example. Assume fade_length is 4, meaning that I apply my fade-in over the first four samples (samples numbered 0 to 3). Both channels of those samples should be multiplied by the following factors to generate the fade-in:

Sample NumberMultiply By...
00.0
10.25
20.5
30.75
3 | Do Not Modify the sample

Grading fade_in

The fade_in function is worth <#points 6 pts>, broken down as follows.

  • Correct fading in effect. <#points 2 pts>
  • Fading effect only for the specified number of samples. <#points 2 pts>
  • Original sound not modified. <#points 1 pts>
  • Correct docstring comment at beginning of function and appropriate comments in the function body. <#points 1 pt>

Fade-out

Now you will need to write a fade_out function, with header given below.

def fade_out(snd, fade_length):

This function again takes a sound object and an integer indicating the length of the fade. However, this time, the fade is a fade-out (from loud to quiet), and the fade-out begins fade_length samples from the end of the sound rather than from the beginning. For example, if fade_length is 88200 and the length of the sound is samp samples, the fade-out should only affect samples numbered samp-88200 up to samp-1.

Let's use a raining sound to demonstrate (rain.wav). As with the water bubbling above, the volume is stable throughout. Now, with the call fade_out(rain, 88200) (where rain is a sound object loaded with the rain sound), we get rain with a short fade-out. The first few seconds of the rain are as before. Then two seconds before the end the fade-out starts, with the sound progressing toward zero volume. The final sample of the sound has value 0.

The multiplicative factors for fade_out are the same as for fade_in, but are applied in the reverse order. For example, if fade_length were 4, the channels of the fourth-last sample would be multiplied by 0.75, the channels of the third-last sample would be multiplied by 0.5, the channels of the second-last sample would be multiplied by 0.25, and the channels of the final sample in the sound would be multiplied by 0.0.

Grading fade_out

The fade_out function is worth <#points 6 pts>, broken down as follows.

  • Correct fading out effect. <#points 2 pts>
  • Fading effect only for the specified number of samples. <#points 2 pts>
  • Original sound not modified. <#points 1 pts>
  • Correct docstring comment at beginning of function and appropriate comments in the function body. <#points 1 pt>

Fade

For the last part of this problem, you will write a function named fade.

def fade(snd, fade_length):

This one combines both fading-in and fading-out. It applies a fade-in of fade_length samples to the beginning of the sound, and applies a fade-out of fade_length samples to the end of the sound. Don't be concerned about what to do when the fades would overlap; don't do anything special to try to recognize or fix this.

To avoid duplication of code, your implementation of fade must make calls to your fade_in and fade_out function.

Try out your fade on one more wav file (grace.wav). This one has a particularly abrupt beginning and end, which your fade function should be able to nicely finesse. This is a large file and can take a minute or two to process on a slow computer; test with smaller files first.

Grading fade

The fade function is worth <#points 4 pts>, broken down as follows.

  • Correct fading out effect. <#points 1 pt>
  • Fading effect only for the specified number of samples. <#points 1 pt>
  • Uses fade_in and fade_out functions to implement this function. <#points 1 pt>
  • Correct docstring comment at beginning of function and appropriate comments in the function body. <#points 1 pt>

Problem 3: Panning from Left to Right

In this problem, you will write a single function that creates a panning effect, where sound moves from the left speaker to the right speaker. As in the previous problems, the function in this part should not modify the sound object it is passed; it should create and return a new sound object.

def left_to_right(snd, pan_length):

This function takes a sound object and an integer indicating the number of samples to which the pan will be applied. For example, if pan_length is 88200, the pan should not affect any sample numbered 88200 or higher.

Let's listen to what panning sounds like. Here's an airplane sound (airplane.wave). The entire sound is centred, and does not move in the stereo field as you listen. Now, with the call left_to_right(airplane, len(airplane)) (where airplane is a sound object loaded with the airplane sound), we get this airplane panning from left to right sound. The sound starts completely at the left, then slowly moves to the right, reaching the extreme right by the final sample.

Getting a sound to move from left to right like this requires a fade-out on the left channel and a fade-in on the right channel.

Here's an example. Assume pan_length is 4. The following table indicates the factors by which the channels of these samples should be multiplied:

Sample NumberMultiply Left Channel By...Multiply Right Channel By...
00.750.0
10.50.25
20.250.5
30.00.75
3 | Do Not Modify the sample | Do Not Modify the sample

If you run left_to_right on only a prefix of a sound (i.e. you use a pan_length that is less than the length of snd), you'll get strange (though expected) results. For example, if you pan the first 441000 samples of love.wav, you'll hear it pan from left to right over the first ten seconds, then you'll hear a click followed by the remainder of the song played in the centre.

To understand how this function works, it might help to think of changing the volume using two volume controls: one for the left channel and one for the right. To make the sound seem like it's moving from left to right, you slowly lower the volume in the left ear and raise the volume in the right ear. There is no copying going on between the two channels. And for the record, this technique only works when corresponding samples of both channels are the same: experiment with this dog and lake sound (doglake.wav) to see what happens when channels contain different sounds.

Grading left_to_right

The left_to_right function is worth <#points 4 pts>, broken down as follows.

  • Correct panning effect. <#points 2 pts>
  • Panning effect only for the specified number of samples. <#points 1 pts>
  • Correct docstring comment at beginning of function and appropriate comments in the function body. <#points 1 pt>

User generated content is uploaded by users for the purposes of learning and should be used following Studypool's honor code & terms of service.

Explanation & Answer

At...


Anonymous
Very useful material for studying!

Studypool
4.7
Trustpilot
4.5
Sitejabber
4.4

Similar Content

Related Tags