# DecibelsChallenge_PersonalData

For the third Decibels Challenge, the prompt for data is personal data. I decided to use data from 10 workouts I did and use **SonicPi** to sonify the process and **Python** to clean it up.

Wanted the sounds to represent the various stages a heart goes through in a workout. This explains some of the chaotic tension/feelings that can be heard in this track

## Sounds

<iframe width="100%" height="300" src="https://w.soundcloud.com/player/?url=https%3A//api.soundcloud.com/tracks/1467050401&color=%23ff5500&auto_play=false&hide_related=false&show_comments=true&show_user=true&show_reposts=false&show_teaser=true&visual=true"></iframe>

[IllestPreacha](https://soundcloud.com/llestreacha) · [Decibels 2023 March Challenge ; Personal Data : Heart Edition](https://soundcloud.com/llestreacha/decibels-2023-march-challenge-personal-data-heart-edition)

### **Data**

### Table

<table><tbody><tr><td colspan="1" rowspan="1"><p></p></td><td colspan="1" rowspan="1"><p>HR_AVG</p></td><td colspan="1" rowspan="1"><p>HR_MAX</p></td><td colspan="1" rowspan="1"><p>HR_MIN</p></td><td colspan="1" rowspan="1"><p>Calories</p></td><td colspan="1" rowspan="1"><p>CardioLoad</p></td><td colspan="1" rowspan="1"><p>Zone3</p></td><td colspan="1" rowspan="1"><p>Zone2</p></td><td colspan="1" rowspan="1"><p>HR_Max-MIn</p></td><td colspan="1" rowspan="1"><p>Zone2+3</p></td><td colspan="1" rowspan="1"><p>Other Zones</p></td><td colspan="1" rowspan="1"><p>CaloLoad</p></td></tr><tr><td colspan="1" rowspan="1"><p>0</p></td><td colspan="1" rowspan="1"><p>147</p></td><td colspan="1" rowspan="1"><p>174</p></td><td colspan="1" rowspan="1"><p>98</p></td><td colspan="1" rowspan="1"><p>554</p></td><td colspan="1" rowspan="1"><p>71</p></td><td colspan="1" rowspan="1"><p>0.44</p></td><td colspan="1" rowspan="1"><p>0.1</p></td><td colspan="1" rowspan="1"><p>76</p></td><td colspan="1" rowspan="1"><p>0.54</p></td><td colspan="1" rowspan="1"><p>0.46</p></td><td colspan="1" rowspan="1"><p>7.802816901</p></td></tr><tr><td colspan="1" rowspan="1"><p>1</p></td><td colspan="1" rowspan="1"><p>123</p></td><td colspan="1" rowspan="1"><p>156</p></td><td colspan="1" rowspan="1"><p>108</p></td><td colspan="1" rowspan="1"><p>876</p></td><td colspan="1" rowspan="1"><p>80</p></td><td colspan="1" rowspan="1"><p>0.36</p></td><td colspan="1" rowspan="1"><p>0.37</p></td><td colspan="1" rowspan="1"><p>48</p></td><td colspan="1" rowspan="1"><p>0.73</p></td><td colspan="1" rowspan="1"><p>0.27</p></td><td colspan="1" rowspan="1"><p>10.95</p></td></tr><tr><td colspan="1" rowspan="1"><p>2</p></td><td colspan="1" rowspan="1"><p>110</p></td><td colspan="1" rowspan="1"><p>135</p></td><td colspan="1" rowspan="1"><p>74</p></td><td colspan="1" rowspan="1"><p>44</p></td><td colspan="1" rowspan="1"><p>3</p></td><td colspan="1" rowspan="1"><p>0.16</p></td><td colspan="1" rowspan="1"><p>0.61</p></td><td colspan="1" rowspan="1"><p>61</p></td><td colspan="1" rowspan="1"><p>0.77</p></td><td colspan="1" rowspan="1"><p>0.23</p></td><td colspan="1" rowspan="1"><p>14.66666667</p></td></tr><tr><td colspan="1" rowspan="1"><p>3</p></td><td colspan="1" rowspan="1"><p>100</p></td><td colspan="1" rowspan="1"><p>126</p></td><td colspan="1" rowspan="1"><p>80</p></td><td colspan="1" rowspan="1"><p>224</p></td><td colspan="1" rowspan="1"><p>16</p></td><td colspan="1" rowspan="1"><p>0</p></td><td colspan="1" rowspan="1"><p>0.12</p></td><td colspan="1" rowspan="1"><p>46</p></td><td colspan="1" rowspan="1"><p>0.12</p></td><td colspan="1" rowspan="1"><p>0.88</p></td><td colspan="1" rowspan="1"><p>14</p></td></tr><tr><td colspan="1" rowspan="1"><p>4</p></td><td colspan="1" rowspan="1"><p>130</p></td><td colspan="1" rowspan="1"><p>156</p></td><td colspan="1" rowspan="1"><p>74</p></td><td colspan="1" rowspan="1"><p>292</p></td><td colspan="1" rowspan="1"><p>29</p></td><td colspan="1" rowspan="1"><p>0.56</p></td><td colspan="1" rowspan="1"><p>0.38</p></td><td colspan="1" rowspan="1"><p>82</p></td><td colspan="1" rowspan="1"><p>0.94</p></td><td colspan="1" rowspan="1"><p>0.06</p></td><td colspan="1" rowspan="1"><p>10.06896552</p></td></tr><tr><td colspan="1" rowspan="1"><p>5</p></td><td colspan="1" rowspan="1"><p>116</p></td><td colspan="1" rowspan="1"><p>140</p></td><td colspan="1" rowspan="1"><p>95</p></td><td colspan="1" rowspan="1"><p>137</p></td><td colspan="1" rowspan="1"><p>11</p></td><td colspan="1" rowspan="1"><p>0.05</p></td><td colspan="1" rowspan="1"><p>0.72</p></td><td colspan="1" rowspan="1"><p>45</p></td><td colspan="1" rowspan="1"><p>0.77</p></td><td colspan="1" rowspan="1"><p>0.23</p></td><td colspan="1" rowspan="1"><p>12.45454545</p></td></tr><tr><td colspan="1" rowspan="1"><p>6</p></td><td colspan="1" rowspan="1"><p>126</p></td><td colspan="1" rowspan="1"><p>158</p></td><td colspan="1" rowspan="1"><p>93</p></td><td colspan="1" rowspan="1"><p>434</p></td><td colspan="1" rowspan="1"><p>42</p></td><td colspan="1" rowspan="1"><p>0.34</p></td><td colspan="1" rowspan="1"><p>0.49</p></td><td colspan="1" rowspan="1"><p>65</p></td><td colspan="1" rowspan="1"><p>0.83</p></td><td colspan="1" rowspan="1"><p>0.17</p></td><td colspan="1" rowspan="1"><p>10.33333333</p></td></tr><tr><td colspan="1" rowspan="1"><p>7</p></td><td colspan="1" rowspan="1"><p>123</p></td><td colspan="1" rowspan="1"><p>154</p></td><td colspan="1" rowspan="1"><p>86</p></td><td colspan="1" rowspan="1"><p>593</p></td><td colspan="1" rowspan="1"><p>58</p></td><td colspan="1" rowspan="1"><p>0.44</p></td><td colspan="1" rowspan="1"><p>0.31</p></td><td colspan="1" rowspan="1"><p>68</p></td><td colspan="1" rowspan="1"><p>0.75</p></td><td colspan="1" rowspan="1"><p>0.25</p></td><td colspan="1" rowspan="1"><p>10.22413793</p></td></tr><tr><td colspan="1" rowspan="1"><p>8</p></td><td colspan="1" rowspan="1"><p>136</p></td><td colspan="1" rowspan="1"><p>136</p></td><td colspan="1" rowspan="1"><p>85</p></td><td colspan="1" rowspan="1"><p>570</p></td><td colspan="1" rowspan="1"><p>69</p></td><td colspan="1" rowspan="1"><p>0.24</p></td><td colspan="1" rowspan="1"><p>0.17</p></td><td colspan="1" rowspan="1"><p>51</p></td><td colspan="1" rowspan="1"><p>0.41</p></td><td colspan="1" rowspan="1"><p>0.59</p></td><td colspan="1" rowspan="1"><p>8.260869565</p></td></tr><tr><td colspan="1" rowspan="1"><p>9</p></td><td colspan="1" rowspan="1"><p>90</p></td><td colspan="1" rowspan="1"><p>123</p></td><td colspan="1" rowspan="1"><p>73</p></td><td colspan="1" rowspan="1"><p>157</p></td><td colspan="1" rowspan="1"><p>12</p></td><td colspan="1" rowspan="1"><p>0</p></td><td colspan="1" rowspan="1"><p>0.15</p></td><td colspan="1" rowspan="1"><p>50</p></td><td colspan="1" rowspan="1"><p>0.15</p></td><td colspan="1" rowspan="1"><p>0.85</p></td><td colspan="1" rowspan="1"><p>13.08333333</p></td></tr><tr><td colspan="1" rowspan="1"><p>10</p></td><td colspan="1" rowspan="1"><p>138</p></td><td colspan="1" rowspan="1"><p>172</p></td><td colspan="1" rowspan="1"><p>108</p></td><td colspan="1" rowspan="1"><p>497</p></td><td colspan="1" rowspan="1"><p>57</p></td><td colspan="1" rowspan="1"><p>0.64</p></td><td colspan="1" rowspan="1"><p>0.16</p></td><td colspan="1" rowspan="1"><p>64</p></td><td colspan="1" rowspan="1"><p>0.8</p></td><td colspan="1" rowspan="1"><p>0.2</p></td><td colspan="1" rowspan="1"><p>8.719298246</p></td></tr></tbody></table>

### Column Names

* HR\_AVG - Average Heart Rate
    
* HR\_Max - Max Heart Rate
    
* HR\_Min - Min Heart Rate
    
* Calories - Calories Burnt
    
* CardioLoad - the cardio intensity given for that workout
    
* Zone2, Zone3, Other Zones - Refer to the Five Heart zones
    
* CaloLoad - Is the ratio of Calories Burnt: Cardio Load
    

These columns are used in the **SonicPi** Code to make the sounds and can be used to understand which columns are affecting which part

## Code

### SonicPi Code

Comments in Code for more information

```ruby
require 'csv'

#naming the Dataset DipInCode and going to read the file
Heart = CSV.parse(File.read("C:/Creatuve Code Challenges/Sonification Challenges/March 2023/HeartRatePrep.csv"), headers: true)


i = 0


live_loop :HeartZone do
  
  #these effects are going to be affected by the zones, since they are between 0 and 1, which is the range for the mix function
  with_fx :echo, mix: Heart[i]['Other Zones'].to_f  do
    with_fx :ixi_techno, mix: Heart[i]['Zone3'].to_f do
      with_fx :krush, mix: Heart[i]['Zone2+3'].to_f do
        
        #a trio of synths to add more musicality/variance to the listening experience
        use_synth [:organ_tonewheel,:mod_sine,:mod_sine].choose
        
        #Corresponds to the note being played
        play Heart[i]['HR_MIN'].to_f, decay: Heart[i]['Other Zones'].to_f, amp: dice(12)
        #We can even pass a list of times which it will treat as a circle of times:
        play_pattern_timed chord(Heart[i]['HR_MIN'].to_f, :m13), [Heart[i]['Zone2+3'].to_f, Heart[i]['Other Zones'].to_f ,Heart[i]['HR_MAX'].to_f/ Heart[i]['HR_MIN'].to_f]
      end
    end
  end
  
  i += 1 #counter
  
  if i == Heart.length #make the loop nonstop
    i = 0
  end
  
  #spacing
  sleep Math.sin(Heart[i]['HR_MAX'].to_f/ Heart[i]['HR_MIN'].to_f)
end


live_loop :HeartBeat do
  
#same as the previous loop, with the difference being a random choosing of 3 effects instead of 3 synths in this portion 

  with_fx :flanger, depth: Heart[i]['Other Zones'].to_f  do
    with_fx :echo,  mix: Heart[i]['Zone2+3'].to_f do
      with_fx [:ping_pong,:vowel,:whammy].choose, mix: Heart[i]['Other Zones'].to_f do
        sample :ambi_piano,beat_stretch: Heart[i]['Zone2'].to_f ,pitch: Heart[i]['CaloLoad'].to_f
        sample :perc_impact1,beat_stretch: Math.cos(Heart[i]['Other Zones'].to_f), decay: Heart[i]['CaloLoad'].to_f
      end
    end
  end
  
  i += 1
  
  if i == Heart.length #make the loop nonstop
    i = 0
  end
  
  sleep Heart[i]['HR_MAX'].to_f/ Heart[i]['HR_MIN'].to_f
end
```

### Python Code

```python
import pandas as pd
```

```python
df = pd.read_csv('Jan16_23_heart - Sheet1.csv')
```

```python
df.info()
```

&lt;class 'pandas.core.frame.DataFrame'&gt; RangeIndex: 11 entries, 0 to 10 Data columns (total 7 columns): # Column Non-Null Count Dtype  
\--- ------ -------------- -----  
0 HR\_AVG 11 non-null int64  
1 HR\_MAX 11 non-null int64  
2 HR\_MIN 11 non-null int64  
3 Calories 11 non-null int64  
4 CardioLoad 11 non-null int64  
5 Zone3 11 non-null float64 6 Zone2 11 non-null float64 dtypes: float64(2), int64(5) memory usage: 744.0 bytes

```python
df. describe()
```

|  | HR\_AVG | HR\_MAX | HR\_MIN | Calories | CardioLoad | Zone3 | Zone2 |
| --- | --- | --- | --- | --- | --- | --- | --- |
| count | 11.000000 | 11.000000 | 11.000000 | 11.000000 | 11.000000 | 11.000000 | 11.000000 |
| mean | 121.727273 | 148.181818 | 88.545455 | 398.000000 | 40.727273 | 0.293636 | 0.325455 |
| std | 16.870631 | 17.325231 | 12.902431 | 249.911184 | 27.756408 | 0.222003 | 0.210778 |
| min | 90.000000 | 123.000000 | 73.000000 | 44.000000 | 3.000000 | 0.000000 | 0.100000 |
| 25% | 113.000000 | 135.500000 | 77.000000 | 190.500000 | 14.000000 | 0.105000 | 0.155000 |
| 50% | 123.000000 | 154.000000 | 86.000000 | 434.000000 | 42.000000 | 0.340000 | 0.310000 |
| 75% | 133.000000 | 157.000000 | 96.500000 | 562.000000 | 63.500000 | 0.440000 | 0.435000 |
| max | 147.000000 | 174.000000 | 108.000000 | 876.000000 | 80.000000 | 0.640000 | 0.720000 |

```python
#time to make new columns based on the information provided and get more Numbers for the sonification


#HeartRate Max-MIn , getting the difference between Heart Rates
df['HR_Max-MIn'] = df['HR_MAX']- df['HR_MIN'] 

#Total percentage of HeartRatein Zone3 + Zone2
df['Zone2+3'] = df['Zone2'] + df['Zone3'] 

#Total percentage of Other Heart Zones
df['Other Zones'] = 1 - df['Zone2'] - df['Zone3'] 

#Calories divided by Cardio Load
df['CaloLoad'] = df['Calories'] / df['CardioLoad']
```

```python
df
```

|  | HR\_AVG | HR\_MAX | HR\_MIN | Calories | CardioLoad | Zone3 | Zone2 | HR\_Max-MIn | Zone2+3 | Other Zones | CaloLoad |
| --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- | --- |
| 0 | 147 | 174 | 98 | 554 | 71 | 0.44 | 0.10 | 76 | 0.54 | 0.46 | 7.802817 |
| 1 | 123 | 156 | 108 | 876 | 80 | 0.36 | 0.37 | 48 | 0.73 | 0.27 | 10.950000 |
| 2 | 110 | 135 | 74 | 44 | 3 | 0.16 | 0.61 | 61 | 0.77 | 0.23 | 14.666667 |
| 3 | 100 | 126 | 80 | 224 | 16 | 0.00 | 0.12 | 46 | 0.12 | 0.88 | 14.000000 |
| 4 | 130 | 156 | 74 | 292 | 29 | 0.56 | 0.38 | 82 | 0.94 | 0.06 | 10.068966 |
| 5 | 116 | 140 | 95 | 137 | 11 | 0.05 | 0.72 | 45 | 0.77 | 0.23 | 12.454545 |
| 6 | 126 | 158 | 93 | 434 | 42 | 0.34 | 0.49 | 65 | 0.83 | 0.17 | 10.333333 |
| 7 | 123 | 154 | 86 | 593 | 58 | 0.44 | 0.31 | 68 | 0.75 | 0.25 | 10.224138 |
| 8 | 136 | 136 | 85 | 570 | 69 | 0.24 | 0.17 | 51 | 0.41 | 0.59 | 8.260870 |
| 9 | 90 | 123 | 73 | 157 | 12 | 0.00 | 0.15 | 50 | 0.15 | 0.85 | 13.083333 |
| 10 | 138 | 172 | 108 | 497 | 57 | 0.64 | 0.16 | 64 | 0.80 | 0.20 | 8.719298 |

```python
df.to_csv('HeartRatePrep.csv')
```
