<?xml version="1.0" encoding="UTF-8"?>
<rdf:RDF xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns="http://purl.org/rss/1.0/" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel rdf:about="https://community.wolfram.com">
    <title>Community RSS Feed</title>
    <link>https://community.wolfram.com</link>
    <description>RSS Feed for Wolfram Community showing ideas tagged with Audio, Sound and Music sorted by most replies.</description>
    <items>
      <rdf:Seq>
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2774101" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/900782" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1967207" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2153362" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1732586" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/3062403" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2166833" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1862464" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1730213" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/3062832" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1380021" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1383518" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2318363" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/917048" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1247481" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2328597" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2228704" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/2386951" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/1383630" />
        <rdf:li rdf:resource="https://community.wolfram.com/groups/-/m/t/3299985" />
      </rdf:Seq>
    </items>
  </channel>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2774101">
    <title>[WSG23] Daily Study Group: Wolfram Language Basics</title>
    <link>https://community.wolfram.com/groups/-/m/t/2774101</link>
    <description>A Wolfram U daily study group covering the implementation of Wolfram Language for tasks ranging from basic programming to video analysis begins on January 17, 2023 and runs through February 3. This study group will run on weekdays from 11:00AM&amp;#x2013;12:00PM Central US time.&#xD;
&#xD;
This study group is an incredible way either to start learning Wolfram Language or to explore new functionality you haven&amp;#039;t yet used. We will cover a very broad variety of topics, including but not limited to image and sound analysis, symbolics and numerics, function visualization and even cloud computation and deployment. We will even cover useful tips and tricks to help you work efficiently with notebooks!&#xD;
&#xD;
![enter image description here][1]&#xD;
&#xD;
**No prior Wolfram Language experience is necessary.** As usual, we will have questions, study materials, quizzes along the way to help you master the subject matter. &#xD;
&#xD;
You can [**REGISTER HERE**][2]. I hope to see you there!&#xD;
&#xD;
![enter image description here][3]&#xD;
&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=meechstogram.png&amp;amp;userId=1711324&#xD;
  [2]: https://www.bigmarker.com/series/daily-study-group-wolfram-language-basics-wsg34/series_details?utm_bmcr_source=community&#xD;
  [3]: https://community.wolfram.com//c/portal/getImageAttachment?filename=WolframUBanner%281%29%281%29.jpeg&amp;amp;userId=1711324</description>
    <dc:creator>Arben Kalziqi</dc:creator>
    <dc:date>2023-01-11T04:29:36Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/900782">
    <title>Mathematica 11 Release</title>
    <link>https://community.wolfram.com/groups/-/m/t/900782</link>
    <description>Mathematica 11 is now out and ready to compute! Since the release of Version 10 two years ago, Mathematica has grown by leaps and bounds, with 500+ new functions. This version introduces both enhancements to computations across the board and completely new areas of functionality, continuing Mathematica&amp;#039;s growth as the state-of-the-art technical platformand we are very excited to share these developments with the world. Some of the most notable features include:&#xD;
&#xD;
**[3D Printing][1]** &#xD;
&#xD;
![3D-Printed Triceratops][2]&#xD;
&#xD;
 - Print your 3D models to local printers or online printing services with [Printout3D][3].&#xD;
 - Use [FindMeshDefects][4] and [RepairMesh][5] to fix your models before printing.&#xD;
 - Hollow your models out with [ShellRegion][6] to lower the printing cost.&#xD;
&#xD;
**[Computational Audio][7]**&#xD;
&#xD;
![Audio Image][8]&#xD;
&#xD;
 - Version 11 includes a brand-new [Audio][9] object to represent audio created from importing or an array of data.&#xD;
 - Edit your audio with [AudioPad][10], [AudioTrim][11], [AudioSplit][12], [AudioResample][13], etc.&#xD;
 - Synthesize sounds using the new [AudioGenerator][14] function.&#xD;
 - Apply filters, take [AudioMeasurements][15] and visualize your audio with [AudioPlot][16].&#xD;
&#xD;
**[Neural Networks][17]**&#xD;
&#xD;
![Neural Network][18]&#xD;
&#xD;
 - Define network topologies with [NetGraph][19] or with a chain of layers with [NetChain][20].&#xD;
 - Train your neural nets with [NetTrain][21].&#xD;
 - Train networks on either CPUs or NVIDIA GPUs.&#xD;
 - Are your training sets of images too large to hold in-memory? The neural network functions support out-of-core image datasets.&#xD;
&#xD;
**[Improved Machine Learning][22]**&#xD;
&#xD;
![Identifying Notable Celebrities][23]&#xD;
&#xD;
 - [ImageIdentify][24] now recognizes over 10,000 objects.&#xD;
 - Extract features from images, text and other data types using [FeatureExtract][25].&#xD;
 - [Classify][26] works even better with images, including an option to customize what [FeatureExtractor][27] it uses.&#xD;
 - Find formulas for time series data using [FindFormula][28].&#xD;
 - Find clusters in your data with enhanced options for [FindClusters][29], including new methods and setting a [CriterionFunction][30].&#xD;
&#xD;
And these are only just a sample of the new features, including the [Wolfram Channel Framework][31], enhanced notebook processing, cloud-aware [WolframScript][32], improved [symbolic and numeric calculus][33] and so much more.&#xD;
&#xD;
To read more about what&amp;#039;s new in Mathematica 11, read Stephen Wolfram&amp;#039;s [release-day blog post][34] and check out the [New in 11 page][35].&#xD;
&#xD;
&#xD;
  [1]: http://www.wolfram.com/language/11/3d-printing/&#xD;
  [2]: http://community.wolfram.com//c/portal/getImageAttachment?filename=triceratops.png&amp;amp;userId=900759&#xD;
  [3]: http://reference.wolfram.com/language/ref/Printout3D.html&#xD;
  [4]: http://reference.wolfram.com/language/ref/FindMeshDefects.html&#xD;
  [5]: http://reference.wolfram.com/language/ref/RepairMesh.html&#xD;
  [6]: http://reference.wolfram.com/language/ref/ShellRegion.html&#xD;
  [7]: http://www.wolfram.com/language/11/computational-audio/&#xD;
  [8]: http://community.wolfram.com//c/portal/getImageAttachment?filename=audioplot.png&amp;amp;userId=900759&#xD;
  [9]: http://reference.wolfram.com/language/ref/Audio.html&#xD;
  [10]: http://reference.wolfram.com/language/ref/AudioPad.html&#xD;
  [11]: http://reference.wolfram.com/language/ref/AudioTrim.html&#xD;
  [12]: http://reference.wolfram.com/language/ref/AudioSplit.html&#xD;
  [13]: http://reference.wolfram.com/language/ref/AudioResample.html&#xD;
  [14]: http://reference.wolfram.com/language/ref/AudioGenerator.html&#xD;
  [15]: http://reference.wolfram.com/language/ref/AudioMeasurements.html&#xD;
  [16]: http://reference.wolfram.com/language/ref/AudioPlot.html&#xD;
  [17]: http://www.wolfram.com/language/11/neural-networks/&#xD;
  [18]: http://community.wolfram.com//c/portal/getImageAttachment?filename=neuralnetworkdigits.png&amp;amp;userId=900759&#xD;
  [19]: http://reference.wolfram.com/language/ref/NetGraph.html&#xD;
  [20]: http://reference.wolfram.com/language/ref/NetChain.html&#xD;
  [21]: http://reference.wolfram.com/language/ref/NetTrain.html&#xD;
  [22]: http://www.wolfram.com/language/11/improved-machine-learning/&#xD;
  [23]: http://community.wolfram.com//c/portal/getImageAttachment?filename=CumberbatchMachineLearning.png&amp;amp;userId=900759&#xD;
  [24]: http://reference.wolfram.com/language/ref/ImageIdentify.html&#xD;
  [25]: http://reference.wolfram.com/language/ref/FeatureExtract.html&#xD;
  [26]: http://reference.wolfram.com/language/ref/Classify.html&#xD;
  [27]: http://reference.wolfram.com/language/ref/FeatureExtractor.html&#xD;
  [28]: http://reference.wolfram.com/language/ref/FindFormula.html&#xD;
  [29]: http://reference.wolfram.com/language/ref/FindClusters.html&#xD;
  [30]: http://reference.wolfram.com/language/ref/CriterionFunction.html&#xD;
  [31]: http://reference.wolfram.com/language/guide/Channel-BasedCommunication.html&#xD;
  [32]: http://reference.wolfram.com/language/ref/program/wolframscript.html&#xD;
  [33]: http://www.wolfram.com/language/11/symbolic-and-numeric-calculus/&#xD;
  [34]: http://blog.wolfram.com/2016/08/08/today-we-launch-version-11/&#xD;
  [35]: http://www.wolfram.com/mathematica/new-in-11/</description>
    <dc:creator>Zachary Littrell</dc:creator>
    <dc:date>2016-08-08T16:43:43Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1967207">
    <title>Its just a little file in 31 tone equal temperament.</title>
    <link>https://community.wolfram.com/groups/-/m/t/1967207</link>
    <description>I first wrote this code in 1994.  It was version three.  I could not ever get it to run to completion.&#xD;
Puny desktops, and the early versions kept crashing. I got version 12 about a month ago.&#xD;
I finally get to hear what I write.  It has been what? ...30 years.&#xD;
&#xD;
I&amp;#039;m not too bright.  Could anyone help make the code more efficient?&#xD;
&#xD;
I am sorry if I am breaking the community rules...I am desperate...this is my message in a bottle.&#xD;
&#xD;
Best wishes.&#xD;
Patrick Michael Joseph Rose</description>
    <dc:creator>Patrick Rose</dc:creator>
    <dc:date>2020-05-07T11:24:59Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2153362">
    <title>3D Helmholtz resonance in the violin body with f-holes</title>
    <link>https://community.wolfram.com/groups/-/m/t/2153362</link>
    <description>*Wolfram notebook is attached at the end of the post.*&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
![enter image description here][1]&#xD;
&#xD;
This post is about FEM simulation of violin vibration modes in 3D. As well known there are Helmholtz resonances of air inside the violin body with frequencies dependent on geometry of f-holes. This is the main reason why violin has so pronounced sound. To simulate these modes with Mathematica FEM we first define the body geometry (this is my design with given volume and area of f-holes, but it taken from the real violin):&#xD;
&#xD;
    xy = {{3.805405405405406`,3.34954954954955`},{3.8252252252252257`,6.6990990990991`},{3.9441441441441443`,7.9081081081081095`},&#xD;
    {4.47927927927928`,8.601801801801802`},{5.014414414414414`,8.264864864864865`},{4.816216216216216`,7.8882882882882885`},&#xD;
    {4.895495495495496`,7.630630630630631`},{5.232432432432433`,7.432432432432433`},{5.47027027027027`,7.491891891891892`},&#xD;
    {5.648648648648649`,7.8882882882882885`},{5.668468468468468`,8.046846846846847`},{5.56936936936937`,8.403603603603605`},&#xD;
    {5.252252252252252`,8.681081081081082`},{4.855855855855856`,8.780180180180182`},{4.518918918918919`,8.8`},&#xD;
    {3.9639639639639643`,8.522522522522523`},{3.567567567567568`,7.967567567567568`},{3.3693693693693696`,7.372972972972973`},&#xD;
    {3.2306306306306305`,6.67927927927928`},{3.1513513513513516`,3.3693693693693696`},{3.1513513513513516`,2.655855855855856`},&#xD;
    {2.9729729729729732`,1.783783783783784`},{2.8738738738738743`,1.4666666666666668`},{2.100900900900901`,0.7927927927927928`},&#xD;
    {1.7243243243243245`,1.3081081081081083`},{2.021621621621622`,1.7639639639639642`},{2.0414414414414415`,2.0414414414414415`},&#xD;
    {1.9621621621621623`,2.23963963963964`},{1.6648648648648652`,2.4378378378378383`},{1.4666666666666668`,2.5171171171171176`},&#xD;
    {1.10990990990991`,2.338738738738739`},{0.891891891891892`,1.9423423423423425`},{0.9315315315315316`,1.4072072072072073`},&#xD;
    {1.5657657657657658`,0.7927927927927928`},{2.081081081081081`,0.6342342342342343`},{2.5963963963963965`,0.7927927927927928`},&#xD;
    {3.0918918918918923`,1.2090090090090093`},{3.5081081081081082`,1.902702702702703`},{3.706306306306306`,2.6954954954954955`}};&#xD;
    &#xD;
    reg1 = RegionUnion[Disk[{0, 19.5/2}, 19.5/2], &#xD;
      Disk[{0, 36 - 15.5/2}, 15.5/2], &#xD;
      Rectangle[{-10, 15}, {10, 25}]]; reg2 = &#xD;
     RegionDifference[reg1, &#xD;
      RegionUnion[Disk[{-10, 20}, 9.5/2], Disk[{10, 20}, 9.5/2]]];&#xD;
    c0 = {0, 36 - 15.5/2}; c1 = {7.03562, 25}; &#xD;
    f[x_] := c0[[2]] + x (c1[[2]] - c0[[2]])/(c1[[1]] - c0[[1]]); r1 = &#xD;
     Norm[c1 - {10, f[10]}];&#xD;
    reg3 = RegionDifference[reg2, Disk[{10, f[10]}, r1]]; &#xD;
    f1[x_] := c0[[2]] - x (c1[[2]] - c0[[2]])/(c1[[1]] - c0[[1]]);&#xD;
    reg4 = RegionDifference[reg3, Disk[{-10, f1[-10]}, r1]]; c10 = {0, &#xD;
      19.5/2}; c11 = {8.215838362577491`, 15}; &#xD;
    f11[x_] := c10[[2]] + x (c11[[2]] - c10[[2]])/(c11[[1]] - c10[[1]]);&#xD;
    r2 = Norm[c11 - {10, f11[10]}];&#xD;
    reg5 = RegionDifference[reg4, Disk[{10, f11[10]}, r2]]; &#xD;
    f12[x_] := c10[[2]] - x (c11[[2]] - c10[[2]])/(c11[[1]] - c10[[1]]);&#xD;
    reg6 = RegionDifference[reg5, Disk[{-10, f12[-10]}, r2]]; p6 = &#xD;
     RegionPlot[reg6, AspectRatio -&amp;gt; Automatic];&#xD;
    fh[xf_, yf_] := &#xD;
      RegionUnion[&#xD;
       Polygon[Table[{xy[[i, 1]] - xf, xy[[i, 2]] + yf}, {i, &#xD;
          Length[xy]}]], &#xD;
       Polygon[Table[{-xy[[i, 1]] + xf, xy[[i, 2]] + yf}, {i, &#xD;
          Length[xy]}]]];&#xD;
General view of the violin body from the front and back side&#xD;
&#xD;
    Show[p6, Graphics[fh[7, 12], AspectRatio -&amp;gt; Automatic]] &#xD;
    dz = 3.79; reg8 = &#xD;
     ImplicitRegion[Element[{x, y}, reg6] &amp;amp;&amp;amp; 0 &amp;lt;= z &amp;lt;= dz, {x, y, z}];&#xD;
    mesh3d1 = DiscretizeRegion[reg8, {{-10, 10}, {0, 36}, {0, dz}}]&#xD;
    &#xD;
 ![Figure 1][2]   &#xD;
Next step is the computation of air modes in the violin body with using ` NDEigensystem[]` as follows &#xD;
&#xD;
    ca = 34321(*T=20C*); L = -Laplacian[u[x, y, z], {x, y, z}]; {vals, funs} = &#xD;
    NDEigensystem[{L, &#xD;
    DirichletCondition[u[x, y, z] == 0, &#xD;
    Element[{x, y}, fh[7, 11.49]] &amp;amp;&amp;amp; z == dz]}, u, &#xD;
    Element[{x, y, z}, mesh3d1], 15];&#xD;
&#xD;
 Finally we visualize  first 5 modes and the main mode in 3D &#xD;
&#xD;
    {Table[DensityPlot[funs[[i]][x, y, dz/2], {x, -10, 10}, {y, 0, 36}, &#xD;
      PlotRange -&amp;gt; All, PlotLabel -&amp;gt; ca Sqrt[vals[[i]]]/(2 Pi), &#xD;
      ColorFunction -&amp;gt; &amp;#034;Rainbow&amp;#034;, AspectRatio -&amp;gt; Automatic], {i, 1, &#xD;
      5}],&#xD;
     DensityPlot3D[&#xD;
     funs[[1]][x, y, z], {x, -10, 10}, {y, 0, 36}, {z, 0, dz}, &#xD;
     PlotRange -&amp;gt; All, PlotLabel -&amp;gt; ca Sqrt[vals[[1]]]/(2 Pi), &#xD;
     ColorFunction -&amp;gt; &amp;#034;Rainbow&amp;#034;, AspectRatio -&amp;gt; Automatic, &#xD;
     PlotLegends -&amp;gt; Automatic, PlotPoints -&amp;gt; 100, BoxRatios -&amp;gt; Automatic, &#xD;
     OpacityFunction -&amp;gt; None, Boxed -&amp;gt; False]} &#xD;
![Figure 2][3]&#xD;
Therefore the first mode of 440.033 Hz is close to &amp;#034;A4&amp;#034; (440 Hz) tone. But we expecting &amp;#034;C4&amp;#034; (261.626 Hz), or &amp;#034;C#4&amp;#034; (277.183 Hz). The main reason of this discrepancies could be the wood plate vibration from the back side. Thus we define mesh, parameters of the wood plate and modes as follows&#xD;
&#xD;
    dreg = DiscretizeRegion[reg6, {{-10, 10}, {0, 36}}, &#xD;
      MaxCellMeasure -&amp;gt; .05]&#xD;
    Y = 10.8*10^9; nu = 31/100; rho = 500; h = .003; d = &#xD;
     10^4 Sqrt[Y h^2/(12 rho (1 - nu^2))];Ld2 = {Laplacian[-d u[x, y], {x, y}] + &#xD;
        v[x, y], -d Laplacian[v[x, y], {x, y}]};&#xD;
    &#xD;
    {vals, funs} = &#xD;
      NDEigensystem[{Ld2, DirichletCondition[u[x, y] == 0, True]}, {u, v},&#xD;
        Element[{x, y}, dreg], 5];&#xD;
    &#xD;
    Table[DensityPlot[Re[funs[[i, 1]][x, y]], {x, y} \[Element] dreg, &#xD;
      PlotRange -&amp;gt; All, PlotLabel -&amp;gt; vals[[i]]/(2 Pi), &#xD;
      ColorFunction -&amp;gt; &amp;#034;Rainbow&amp;#034;, AspectRatio -&amp;gt; Automatic], {i, 2, &#xD;
      Length[vals]}]&#xD;
![Figure 3][4]&#xD;
Hence for wood plate we have mode of 259.394 Hz and it is close to C4 tone. &#xD;
&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2021-01-04at1.47.31PM.jpg&amp;amp;userId=20103&#xD;
  [2]: https://community.wolfram.com//c/portal/getImageAttachment?filename=bd9Wx.png&amp;amp;userId=1218692&#xD;
  [3]: https://community.wolfram.com//c/portal/getImageAttachment?filename=w7dPm.png&amp;amp;userId=1218692&#xD;
  [4]: https://community.wolfram.com//c/portal/getImageAttachment?filename=qb3HU.png&amp;amp;userId=1218692</description>
    <dc:creator>Alexander Trounev</dc:creator>
    <dc:date>2021-01-03T23:13:58Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1732586">
    <title>[WSC19] Mood Detection in Human Speech</title>
    <link>https://community.wolfram.com/groups/-/m/t/1732586</link>
    <description>![Feature Space Plot for speech data][1]&#xD;
&#xD;
### *Figure Above: Feature Space Plot for speech data*&#xD;
&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
## Abstract&#xD;
In this project, I aim to design a system which is capable of detecting mood in human speech. Specifically, the system can be trained on a single user&amp;#039;s voice given samples of emotional speech labeled as being angry, happy, or sad. The system is then able to classify future audio clips of the user&amp;#039;s speech as having one of these three moods. I collected voice samples of myself and trained a Classifier Function based on this data. I experimented with many different available methods for the Classifier Function and for audio preprocessing to obtain the most accurate Classifier.&#xD;
&#xD;
## Obtaining Data&#xD;
In this project, I focused on detecting mood for only one user (specifically, myself) since different people may express mood in different ways, leading to confusion for the Classifier. I initially recorded ten speech clips in each mood as training data, and ten different clips in each mood as testing data. I used [Audacity](https://www.audacityteam.org/) to record audio clips in 32-bit floating point resolution, exported as WAV files. If you&amp;#039;re looking to replicate this project, you can use your own data, or use mine, available on [my GitHub repository](https://github.com/vedadehhc/MoodDetector). I later recorded additional clips, as discussed below.&#xD;
&#xD;
## Feature Extraction&#xD;
In order to produce the most accurate Classifier, I extracted features which I thought were most useful to detecting mood. Specifically, I extracted the amplitudes, fundamental frequencies, and formant frequencies of each clip over the length of the clip using [AudioLocalMeasurements](https://reference.wolfram.com/language/ref/AudioLocalMeasurements.html). That is, I took multiple measurements of each of these values, over many partitions of the clip. I partitioned each clip into 75 parts, but feel free to experiment with different values. I also found the word rate, using Wolfram Language&amp;#039;s experimental [SpeechRecognize](https://reference.wolfram.com/language/ref/SpeechRecognize.html) function, and the ratio of pausing time to total time of the clip using [AudioIntervals](https://reference.wolfram.com/language/ref/AudioIntervals.html). The final function takes the location of the audio file (could be local or on the web) and the number of partitions, and returns an association with the extracted features. It&amp;#039;s important that the function return an association, since this makes things much easier when constructing the Classifier Function. The initial function for feature extraction is included below.&#xD;
&#xD;
    extractFeatures[fileLocation_, parts_] :=  &#xD;
     Module[{audio, assoc, pdur, amp, freq, form}, &#xD;
      audio = Import[fileLocation];&#xD;
      pdur = AudioMeasurements[audio, &amp;#034;Duration&amp;#034;]/parts;&#xD;
      amp = AudioLocalMeasurements[audio, &amp;#034;RMSAmplitude&amp;#034;, &#xD;
         PartitionGranularity -&amp;gt; pdur] // Normal;&#xD;
      freq = AudioLocalMeasurements[audio, &amp;#034;FundamentalFrequency&amp;#034;, &#xD;
         MissingDataMethod -&amp;gt; {&amp;#034;Interpolation&amp;#034;, InterpolationOrder -&amp;gt; 1}, &#xD;
         PartitionGranularity -&amp;gt; pdur] // Normal;&#xD;
      form =  &#xD;
       AudioLocalMeasurements[audio, &amp;#034;Formants&amp;#034;, &#xD;
         PartitionGranularity -&amp;gt; pdur] // Normal;&#xD;
      assoc = &amp;lt;|&#xD;
        Table[&amp;#034;amplitude&amp;#034; &amp;lt;&amp;gt; ToString[i] -&amp;gt; amp[[i]][[2]], {i, Length[amp]}], &#xD;
        Table[&amp;#034;frequency&amp;#034; &amp;lt;&amp;gt; ToString[i] -&amp;gt; freq[[i]][[2]], {i, Length[freq]}], &#xD;
        &amp;#034;wordrate&amp;#034; -&amp;gt; &#xD;
          Length[TextWords[Quiet[SpeechRecognize[audio]]]]/&#xD;
          AudioMeasurements[audio, &amp;#034;Duration&amp;#034;],&#xD;
        Table[Table[&amp;#034;formant&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;-&amp;#034; &amp;lt;&amp;gt; ToString[j] -&amp;gt;&#xD;
          form[[i]][[j]], {j, Length[form[[i]]]}], {i, Length[form]}],&#xD;
        &amp;#034;pauses&amp;#034; -&amp;gt;  &#xD;
          Total[Abs /@ Subtract @@@ AudioIntervals[audio, &amp;#034;Quiet&amp;#034;]]/&#xD;
          AudioMeasurements[audio, &amp;#034;Duration&amp;#034;]&#xD;
        |&amp;gt;; &#xD;
      Map[Normal, assoc, {1}]&#xD;
    ]&#xD;
&#xD;
### Get Training Data&#xD;
Using this function, I was able get the features for all of my training data. Here, I&amp;#039;ll import my data from [my GitHub repository](https://github.com/vedadehhc/MoodDetector).&#xD;
&#xD;
    angryTrainingFeats = &#xD;
     Table[extractFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
        TrainingData/angry&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, 10}];&#xD;
    happyTrainingFeats = &#xD;
     Table[extractFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TrainingData/happy&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, 10}];&#xD;
    sadTrainingFeats = &#xD;
     Table[extractFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TrainingData/sad&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, 10}];&#xD;
&#xD;
### Get Testing Data&#xD;
I also imported my testing data in the same way, so that it could be passed as an argument to the Classifier Function. I&amp;#039;ll get this from GitHub as well. Note that this is the regular test data on GitHub.&#xD;
&#xD;
    angryTestingFeats =  &#xD;
     Table[extractFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TestingData/Regular/a&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, 10}];&#xD;
    happyTestingFeats =  &#xD;
     Table[extractFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TestingData/Regular/h&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, 10}];&#xD;
    sadTestingFeats =  &#xD;
     Table[extractFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TestingData/Regular/s&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, 10}];&#xD;
&#xD;
## Training a Classifier&#xD;
I constructed a Classifier Function using [Classify](https://reference.wolfram.com/language/ref/Classify.html).&#xD;
&#xD;
    classifier = &#xD;
     Classify[&amp;lt;|&amp;#034;angry&amp;#034; -&amp;gt; angryTrainingFeats, &#xD;
       &amp;#034;happy&amp;#034; -&amp;gt; happyTrainingFeats, &amp;#034;sad&amp;#034; -&amp;gt; sadTrainingFeats|&amp;gt;, &#xD;
      Method -&amp;gt; &amp;#034;LogisticRegression&amp;#034;]&#xD;
&#xD;
I ran the classifier on each set of training data.&#xD;
&#xD;
    classifier[angryTrainingFeats]&#xD;
    classifier[happyTrainingFeats]&#xD;
    classifier[sadTrainingFeats]&#xD;
&#xD;
I experimented with all of the built-in options for [Method](https://reference.wolfram.com/language/ref/Method.html) to construct a Classifier Function with the best accuracy. I found that [LogisticRegression](https://reference.wolfram.com/language/ref/method/LogisticRegression.html) gave the best accuracy at 77% accuracy on the test data. However, I wanted to improve the accuracy further.&#xD;
&#xD;
## Audio Pre-Processing&#xD;
One of the things that improved the Classifier&amp;#039;s accuracy substantially was cleaning the audio before extracting features and classifying. Specifically, I trimmed the audio using [AudioTrim](https://reference.wolfram.com/language/ref/AudioTrim.html), and filtered each clip using [HighpassFilter](https://reference.wolfram.com/language/ref/HighpassFilter.html) before extracting features. The audio cleaning function is included below.&#xD;
&#xD;
    cleanAudio[fileLocation_] := Module[{audio, trimmed, filtered},&#xD;
      audio = Import[fileLocation];&#xD;
      trimmed = AudioTrim[audio];&#xD;
      filtered = HighpassFilter[trimmed, Quantity[300, &amp;#034;Hertz&amp;#034;]]&#xD;
    ]&#xD;
&#xD;
### New Feature Extraction Function&#xD;
I updated the feature extraction function to include audio cleaning.&#xD;
&#xD;
    extractCleanFeatures[fileLocation_, parts_] :=  &#xD;
     Module[{audio, assoc, pdur, amp, freq, form}, &#xD;
      audio = cleanAudio[fileLocation];&#xD;
      pdur = AudioMeasurements[audio, &amp;#034;Duration&amp;#034;]/parts;&#xD;
      amp = AudioLocalMeasurements[audio, &amp;#034;RMSAmplitude&amp;#034;, &#xD;
         PartitionGranularity -&amp;gt; pdur] // Normal;&#xD;
      freq = AudioLocalMeasurements[audio, &amp;#034;FundamentalFrequency&amp;#034;, &#xD;
         MissingDataMethod -&amp;gt; {&amp;#034;Interpolation&amp;#034;, InterpolationOrder -&amp;gt; 1}, &#xD;
         PartitionGranularity -&amp;gt; pdur] // Normal;&#xD;
      form =  &#xD;
       AudioLocalMeasurements[audio, &amp;#034;Formants&amp;#034;, &#xD;
         PartitionGranularity -&amp;gt; pdur] // Normal;&#xD;
      assoc = &amp;lt;|&#xD;
        Table[&#xD;
         &amp;#034;amplitude&amp;#034; &amp;lt;&amp;gt; ToString[i] -&amp;gt; amp[[i]][[2]], {i, Length[amp]}], &#xD;
        Table[&#xD;
         &amp;#034;frequency&amp;#034; &amp;lt;&amp;gt; ToString[i] -&amp;gt; freq[[i]][[2]], {i, Length[freq]}], &#xD;
        &amp;#034;wordrate&amp;#034; -&amp;gt; &#xD;
         Length[TextWords[Quiet[SpeechRecognize[audio]]]]/&#xD;
          AudioMeasurements[audio, &amp;#034;Duration&amp;#034;],&#xD;
        Table[&#xD;
         Table[&amp;#034;formant&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;-&amp;#034; &amp;lt;&amp;gt; ToString[j] -&amp;gt; &#xD;
           form[[i]][[j]], {j, Length[form[[i]]]}], {i, Length[form]}],&#xD;
        &amp;#034;pauses&amp;#034; -&amp;gt;  &#xD;
         Total[Abs /@ Subtract @@@ AudioIntervals[audio, &amp;#034;Quiet&amp;#034;]]/&#xD;
          AudioMeasurements[audio, &amp;#034;Duration&amp;#034;]&#xD;
        |&amp;gt;; &#xD;
      Map[Normal, assoc, {1}]&#xD;
    ]&#xD;
&#xD;
### New Results&#xD;
Using audio cleaning, the accuracy of the classifier improved to 90%, much better than before. The results can be seen in the Confusion Matrix Plot below, generated using [ClassifierMeasurements](https://reference.wolfram.com/language/ref/ClassifierMeasurements.html).&#xD;
&#xD;
![Confusion Matrix Plot for Regular Data][2]&#xD;
&#xD;
## Testing with Neutral Statements&#xD;
Now, up until now, the statements used for recordings were all emotional in nature. For example, the clips recorded in an angry mood also had an angry statement being said. In order to control for this, I recorded neutral statements in each mood. That is, I recorded each of ten emotionally neutral statements in each of the three moods. If the Classifier still works on this data, that would show that it is not relying on the content of the speech, but on other audio features, which is the intended method. I imported these data using the clean feature extractor and, once again, I&amp;#039;ll download them from my GitHub here. Note that this is the Neutral Statements data.&#xD;
&#xD;
    nAngryCleanTestingFeats =  &#xD;
      Table[extractCleanFeatures[&#xD;
        &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
        TestingData/NeutralStatements/a&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, &#xD;
        10}];&#xD;
    nHappyCleanTestingFeats =  &#xD;
     Table[extractCleanFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TestingData/NeutralStatements/h&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, &#xD;
       10}];&#xD;
    nSadCleanTestingFeats =  &#xD;
     Table[extractCleanFeatures[&#xD;
       &amp;#034;https://github.com/vedadehhc/MoodDetector/raw/master/AudioData/&#xD;
       TestingData/NeutralStatements/s&amp;#034; &amp;lt;&amp;gt; ToString[i] &amp;lt;&amp;gt; &amp;#034;.wav&amp;#034;, 75], {i, &#xD;
       10}];&#xD;
&#xD;
### Results for Neutral Statements&#xD;
I ran the clean Classifier on the new data, and the results were very positive. The classifier achieved an accuracy of 97% on the Neutral Statements data. The results are displayed in the Confusion Matrix Plot below, generated using [ClassifierMeasurements](https://reference.wolfram.com/language/ref/ClassifierMeasurements.html).&#xD;
&#xD;
![Confusion Matrix Plot for Neutral Statements Data][3]&#xD;
&#xD;
## Conclusions&#xD;
Overall, the Classifier was able to identify mood at 93% accuracy, even when the same statements were spoken in different moods. The composite Confusion Matrix Plot for all testing data can be seen below.&#xD;
&#xD;
![Confusion Matrix Plot for all test data][4]&#xD;
&#xD;
## Future Work&#xD;
In the future, I hope to improve the accuracy of the Classifier by providing additional training data, and to test it further with additional testing data. I also hope to expand the range of moods that the Classifier handles, including moods such as fear, calmness, and excitement. This, of course, would require the aforementioned additional data, and perhaps, more complex structures for the Classifier Function. In the future I would also like to experiment with multiple speakers, and determine whether classifiers for one speaker&amp;#039;s moods can be used to determine those of another speaker.&#xD;
&#xD;
## Acknowledgements&#xD;
I would like to thank my mentor Faizon Zaman for his guidance and assistance on this project.&#xD;
&#xD;
## GitHub&#xD;
You can find my code for this project on [my GitHub repository](https://github.com/vedadehhc/MoodDetector), with all code available beginning July 12th, 2019.&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=featureSpacePlotNoLabel.png&amp;amp;userId=1724789&#xD;
  [2]: https://community.wolfram.com//c/portal/getImageAttachment?filename=CMP1.png&amp;amp;userId=1724789&#xD;
  [3]: https://community.wolfram.com//c/portal/getImageAttachment?filename=CMP2.png&amp;amp;userId=1724789&#xD;
  [4]: https://community.wolfram.com//c/portal/getImageAttachment?filename=CMP3.png&amp;amp;userId=1724789</description>
    <dc:creator>Dev Chheda</dc:creator>
    <dc:date>2019-07-12T01:16:42Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/3062403">
    <title>Direct API access to new features of GPT-4 (including vision, DALL-E, and TTS)</title>
    <link>https://community.wolfram.com/groups/-/m/t/3062403</link>
    <description>![enter image description here][1]&#xD;
&#xD;
&amp;amp;[Wolfram Notebook][2]&#xD;
&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=fg45qw.jpg&amp;amp;userId=11733&#xD;
  [2]: https://www.wolframcloud.com/obj/34ac42c4-10de-4201-a158-6af47eda2bd8</description>
    <dc:creator>Marco Thiel</dc:creator>
    <dc:date>2023-11-08T21:48:25Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2166833">
    <title>Predicting COVID-19 using cough sounds classification</title>
    <link>https://community.wolfram.com/groups/-/m/t/2166833</link>
    <description>&amp;amp;[Wolfram Notebook][1]&#xD;
&#xD;
&#xD;
  [1]: https://www.wolframcloud.com/obj/cdf7d474-f4fb-4cbd-bbd5-f1fac8699f7a</description>
    <dc:creator>Siria Sadeddin</dc:creator>
    <dc:date>2021-01-18T22:46:11Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1862464">
    <title>Using Pseudo-Hilbert Curves to Assist People Perceive Images via Sound</title>
    <link>https://community.wolfram.com/groups/-/m/t/1862464</link>
    <description>###Introduction###&#xD;
Recently, I was learning about infinite space filling curves and their applications in real life. I became fascinated with [Hilbert Curves][1], one of many [plane-filling functions][2]. I wanted to see how these shapes could be used in image to video conversion. To begin with, I explored how pseudo Hilbert Curves could be used to convert a square image to audio so that each pixel color was associated with a specific sound. &#xD;
&#xD;
Theoretically, a person would be able to learn this association and would be able to reconstruct a mental image by listening to audio. This could help with people who are visually impaired, letting blind people &amp;#034;hear&amp;#034; pictures. The reverse is also true. People who are deaf will be able to &amp;#034;see&amp;#034; sound. &#xD;
&#xD;
I thought I could implement this using Mathematica, which I learned last summer at the Wolfram High School Camp.&#xD;
&#xD;
###Why Hilbert Curves###&#xD;
![Pseudo-Hilbert Curves from Order 1 to 10][3]&#xD;
As you can see above, as you increase the order, the limit of these curves start to fill an infinite amount of space. A true Hilbert Curve is actually $\lim_{n\to\infty} PseudoHilbertCurve_n$. Each one of these curves can be used on an image of dimensions 2 by 2, 4 by 4, 8 by 8, etc. The curve needed is accordingly:&#xD;
&#xD;
    HilbertCurve[Log[2, ImageDimensions[image]]]&#xD;
&#xD;
Each line in the curve will go over one pixel in the image, starting at the bottom left and ending at the bottom right. &#xD;
&#xD;
![Example of Order 3 Pseudo Hilbert Curve][4]&#xD;
&#xD;
But why would you need to use this specific pattern, as supposed to something more simple? Here: https://youtu.be/3s7h2MHQtxc?t=355. In short, if you were to increase the resolution of your image, you would now have to retrain your brain to re-associate the pixel value and the associated frequency at that point on the image. But this is not the case on a Hilbert Curve. As you increase the resolution of your image, and thus the order pseudo-Hilbert Curve, a point will just move closer and closer to its limit in the same space, which solves our problem.&#xD;
&#xD;
###Converting Color to Sound###&#xD;
This was the main hurdle when writing the program. I needed to convert each pixel value to a unique sound frequency. My initial thought was to just create an association between each wavelength in the visible electromagnetic spectrum and a frequency, but I was quick to learn that doesn&amp;#039;t work in the digital world. RGB colors could be a combination of different wavelengths. And I couldn&amp;#039;t just add these wavelengths separately because there could be overlap. There was also brightness and darkness which isn&amp;#039;t part of the light spectrum. So instead of the RGB format, I decided to use the HSB format (hue, saturation, and brightness). This is also more compatible for human learning, as the human eye uses these three characteristics to determine color, as supposed to the RGB values on a computer image.&#xD;
&#xD;
![Graphics3D Visualizer of HSB][5]&#xD;
&#xD;
As you can see from the image, Hue could be used to determine the color. Now, instead of RGB with three values to one color, Hue gave me one number to a specific color. &#xD;
&#xD;
![Graphics Hue Color Chart][6]&#xD;
&#xD;
But I still needed to show saturation and brightness in my sound waves. Color in a computer is expressed in three dimensions while sound has two: amplitude and frequency. I would be leaving one color property out. I could think of multiple ways to express all three as sound waves, but none of them made sure that similar colors sounded the same. For example, if I had a hue playing a certain frequency, I could define a range around this point that could express either saturation or brightness using a plus/minus system. &#xD;
&#xD;
To solve this, I decided to use [AudioChannel][7] functions. This way, one channel could express the hue through a specific frequency, while the other channel could express the saturation and brightness combined through volume and frequency respectively. This way, colors that were similar would sound similar too.&#xD;
&#xD;
###Creating the Function###&#xD;
Obviously, I needed to get real images. I used *image1*, where the pixels were easily noticeable, and my baby picture for the school yearbook as *image2*, as a test image. The first one, being resized to a 8 by 8 image, would utilize an order 3 pseudo-Hilbert Curve ($\log _{2}8=3$), and the second one, being resized to a 32 by 32 image, would utilize an order 5 pseudo-Hilbert Curve ($\log _{2}32=5$).&#xD;
&#xD;
![The images I used to test the program.][8]&#xD;
&#xD;
To get the HSB values, I used Wolfram&amp;#039;s in-built [Hilbert Curve][9] and [Pixel Value][10] functions. I used Pixel Value to read the image&amp;#039;s pixel values as bytes, which was converted to RGB and then to HSB. To get the points on the Hilbert Curve that was associated with their respective position on the image, I added {1,1} to each point so that it matched the pixel space (the origin on a Cartesian Plane is designated as (1,1) on an image).&#xD;
&#xD;
    getHSB[image_] := &#xD;
     ColorConvert[&#xD;
      RGBColor /@ &#xD;
       Divide[PixelValue[&#xD;
         image, ({1, 1} + #) &amp;amp; /@ &#xD;
          HilbertCurve[Log[2, ImageDimensions[image][[1]]]][[1]], &amp;#034;Byte&amp;#034;],&#xD;
         255.], &amp;#034;HSB&amp;#034;]&#xD;
&#xD;
In the Wolfram Language, HSB values range from 0 to 1 instead of the normal 0 to 360 which I guess gives the user more control of the specific color they want to implement. I had to scale these values to the frequency range I wanted for the hue and brightness. Through trial and error, I decided that 100-3900 Hz was a good range so that people of all ages could hear the lowest and highest frequencies. For the amplitude dictated by the saturation, I could just use the direct value as [SoundVolume][11]. I made it so that the sound for each pixel had a duration of 0.1 seconds for demonstrative purposes. In the real world, I would think that this should be a lot smaller so that images don&amp;#039;t take too long to hear. &#xD;
&#xD;
    getHSB[image_] := &#xD;
     ColorConvert[&#xD;
      RGBColor /@ &#xD;
       Divide[PixelValue[&#xD;
         image, ({1, 1} + #) &amp;amp; /@ &#xD;
          HilbertCurve[Log[2, ImageDimensions[image][[1]]]][[1]], &amp;#034;Byte&amp;#034;],&#xD;
         255.], &amp;#034;HSB&amp;#034;]&#xD;
    hueToFrequencyMatch[HSB_] := Rescale[HSB[[1]], {0, 1}, {100, 3900}]&#xD;
    saturationToAmplitudeMatch[HSB_] := HSB[[2]]&#xD;
    brightnessToFrequencyMatch[HSB_] := &#xD;
     Rescale[HSB[[3]], {0, 1}, {100, 3900}]&#xD;
    soundFrequency[frequency_] := &#xD;
     Sound[Play[Sin[frequency*2 Pi t], {t, 0, 0.1}]]&#xD;
    soundFrequencyVolume[frequency_, ampSaturation_] := &#xD;
     Sound[soundFrequency[frequency], SoundVolume -&amp;gt; ampSaturation]&#xD;
&#xD;
After this, I just had to apply these functions over the HSB values of each pixel in the order dictated by the appropriate pseudo-Hilbert Curve, and then merge the hue sound and saturation+brightness sound as separate audio channels. &#xD;
&#xD;
    convertHToSound[image_] := &#xD;
     soundFrequency /@ hueToFrequencyMatch /@ getHSB[image] // AudioJoin&#xD;
    convertBSToSound[picture_] :=&#xD;
     (soundList = {}; n = 1;&#xD;
      While[n &amp;lt;= Length@getHSB[picture],&#xD;
       AppendTo[soundList, &#xD;
        soundFrequencyVolume[&#xD;
         getHSB[picture][[n]] // brightnessToFrequencyMatch, &#xD;
         getHSB[picture][[n]] // saturationToAmplitudeMatch]];&#xD;
       n++])&#xD;
    convertHSBToSound[audio1_, audio2_] := &#xD;
     AudioChannelCombine[{audio1, audio2}]&#xD;
&#xD;
Because hue is the most important color characteristic, I wanted to emphasize this AudioChannel more. Thus,&#xD;
&#xD;
    editChannel2[audio_, factor_] := AudioPan[audio, -factor]&#xD;
&#xD;
To put everything together, I made a separate function to organize the results.&#xD;
&#xD;
    seperateTable[picture_] :=&#xD;
     (convertBSToSound[picture];&#xD;
      Module[{a = convertHToSound[picture], b = soundList // AudioJoin},&#xD;
       c = editChannel2[convertHSBToSound[a, b], 0.05];&#xD;
       table = &#xD;
        Grid[{{Image[picture, ImageSize -&amp;gt; 100], a, b, c}, {Blank[], &#xD;
           AudioPlot@a, AudioPlot@b, AudioPlot@c}}];&#xD;
       ReplacePart[table, &#xD;
        1 -&amp;gt; Prepend[&#xD;
          First[table], {&amp;#034;Image&amp;#034;, &amp;#034;Hue&amp;#034;, &amp;#034;Saturation+Brightness&amp;#034;, &#xD;
           &amp;#034;HSB&amp;#034;}]]])&#xD;
&#xD;
These were my results. I will attach the *hsb1* and *hsb2* sound files to this post, along with my notebook. &#xD;
&#xD;
![Final image to sound representation.][12]&#xD;
Because they use two channels, you should use earbuds or headphones so that you can clearly differentiate the sounds coming through your left and right ears.&#xD;
![Spectrogram of *hsb1* and *hsb2*][13]&#xD;
&#xD;
###Visualizing the Process###&#xD;
&#xD;
    animate[image_, audio_] :=&#xD;
        Module[{list = ({1, 1} + #) &amp;amp; /@ &#xD;
        HilbertCurve[Log[2, ImageDimensions[image][[1]]]][[1]]},&#xD;
      (AudioPlay@audio;&#xD;
       Animate[&#xD;
        ReplacePixelValue[Image[image, ImageSize -&amp;gt; 100], &#xD;
         list[[1 ;; index]] -&amp;gt; Orange],&#xD;
        {index, 1, list // Length, 1}, &#xD;
        DefaultDuration -&amp;gt; &#xD;
         QuantityMagnitude[&#xD;
          UnitConvert[Quantity[audio // Duration, &amp;#034;Seconds&amp;#034;]]], &#xD;
        AnimationRepetitions -&amp;gt; 1])]&#xD;
&#xD;
I used this to create the following two animations. If you ran these programs, the HSB sound would play alongside the animation, showing exactly which pixel correlates to each sound. Unfortunately, I couldn&amp;#039;t play the audio here on the post, but it is in the attached notebook if you would like to see. Here is what it looks like:&#xD;
&#xD;
![*hsb1* Conversion][14]&#xD;
![*hsb2* Conversion][15]&#xD;
&#xD;
###Future Work###&#xD;
In the future, I hope to create a machine learning algorithm that can learn this association between audio and image in reverse (recreate the image from audio). If anyone has any ideas or pointers for me, please share in the comments below - I would really appreciate it!&#xD;
&#xD;
##Updated Information:##&#xD;
Presented work at the [New Hampshire Science &amp;amp; Engineering Expo][16] and won the Office of Naval Research award.&#xD;
&#xD;
Youtube Link: [Video Presentation][17]&#xD;
&#xD;
&#xD;
  [1]: http://mathworld.wolfram.com/HilbertCurve.html&#xD;
  [2]: http://mathworld.wolfram.com/Plane-FillingFunction.html&#xD;
  [3]: https://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2020-01-19at12.07.19PM.png&amp;amp;userId=1725131&#xD;
  [4]: https://community.wolfram.com//c/portal/getImageAttachment?filename=example.gif&amp;amp;userId=1725131&#xD;
  [5]: https://community.wolfram.com//c/portal/getImageAttachment?filename=HSB.png&amp;amp;userId=1725131&#xD;
  [6]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Hue.png&amp;amp;userId=1725131&#xD;
  [7]: https://reference.wolfram.com/language/ref/AudioChannels.html&#xD;
  [8]: https://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2020-01-19at1.39.00PM.png&amp;amp;userId=1725131&#xD;
  [9]: https://reference.wolfram.com/language/ref/HilbertCurve.html&#xD;
  [10]: https://reference.wolfram.com/language/ref/PixelValue.html&#xD;
  [11]: https://reference.wolfram.com/language/ref/SoundVolume.html&#xD;
  [12]: https://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2020-01-19at2.23.47PM.png&amp;amp;userId=1725131&#xD;
  [13]: https://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2020-01-19at2.32.49PM.png&amp;amp;userId=1725131&#xD;
  [14]: https://community.wolfram.com//c/portal/getImageAttachment?filename=animation1.gif&amp;amp;userId=1725131&#xD;
  [15]: https://community.wolfram.com//c/portal/getImageAttachment?filename=animation2.gif&amp;amp;userId=1725131&#xD;
  [16]: https://nhsee.org/&#xD;
  [17]: https://youtu.be/gwpK2KIfVmA</description>
    <dc:creator>Srinath Rangan</dc:creator>
    <dc:date>2020-01-19T19:42:34Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1730213">
    <title>[WSS19] OCR for Sheet Music</title>
    <link>https://community.wolfram.com/groups/-/m/t/1730213</link>
    <description># Overview&#xD;
&#xD;
Given an image of some sheet music, generate some internal representation of it that can then be played, reprinted or exported to some external musical notation software.&#xD;
&#xD;
In order to do this, first we split the sheet music into images of each staff, and remove the staff lines; we then find bounding boxes for each musical component&#xD;
using image segmentation, and classify them. This is all then passed to a parser that parses the final sheet music.&#xD;
&#xD;
# Finding the Staffs&#xD;
&#xD;
Staff lines are long, horizontal and thin; as such, they can be highlighted by using a bottom hat transform with a short vertical kernel, and the extracted with `ImageLines`.&#xD;
Then, by looking for close groups of five such lines, we can extract an image for each staff in the original score. We also find the median distance between the staff lines,&#xD;
both for padding the staff images and for reusing later.&#xD;
&#xD;
```&#xD;
detectStaffLineImages[image_] := Module[{&#xD;
   staffLines =&#xD;
    Select[ImageLines[BottomHatTransform[image, BoxMatrix[{1, 0}]],&#xD;
       Automatic, 0.0065][[All,&#xD;
      1]], (Abs@VectorAngle[Subtract @@ #, {-1, 0}] &amp;lt;&#xD;
        10 \[Degree]) &amp;amp;]&#xD;
   },&#xD;
  \[CapitalDelta] =&#xD;
   Median@Differences@Sort@Map[Mean, staffLines[[All, All, 2]]];&#xD;
  staffLineGroups =&#xD;
   Gather[Sort[&#xD;
      staffLines, (Last@Mean@#1 &amp;gt; Last@Mean@#2) &amp;amp;], (Last@Mean@#1 -&#xD;
         Last@Mean@#2 &amp;lt; 5 \[CapitalDelta]) &amp;amp;] // Echo;&#xD;
  {Map[&#xD;
    ImageTrim[image, Flatten[#, 1], {0, 2.25 \[CapitalDelta]}] &amp;amp;,&#xD;
    staffLineGroups&#xD;
    ],&#xD;
   \[CapitalDelta]}&#xD;
  ]&#xD;
```&#xD;
&#xD;
![Original page image][1]&#xD;
&#xD;
![One of the split staff images][2]&#xD;
&#xD;
# Removing the Staff Lines&#xD;
&#xD;
Staff lines are dark, long, thin and horizontal. In order to remove them, we use a dilation with a short vertical kernel and the&#xD;
bottom hat transform of the image with a long horizontal kernel; by considering their closing together with taking the pixel-wise&#xD;
minimum and maximum of the resulting image with its morphological binarization, we get an image of the staff with no staff lines&#xD;
and not many artefacts.&#xD;
&#xD;
```&#xD;
removeStaffLines[image_, \[CapitalDelta]_] :=&#xD;
 With[&#xD;
  {withoutStaffLines =&#xD;
    imageMin[Closing[image, BoxMatrix[{\[CapitalDelta]/6, 0}]],&#xD;
     ColorNegate@&#xD;
      BottomHatTransform[image, BoxMatrix[{0, \[CapitalDelta]}]]]},&#xD;
  imageMax[withoutStaffLines,&#xD;
   MorphologicalBinarize[withoutStaffLines, {0.66, 0.33}]]&#xD;
  ]&#xD;
```&#xD;
&#xD;
![Staffs removed][3]&#xD;
&#xD;
# Finding Bounding Boxes for the Musical Components&#xD;
&#xD;
## Image Segmentation&#xD;
&#xD;
For the image segmentation, we use a SegNet [^segnet] trained on the DeepScores [^deepscores] [Segmentation Dataset](https://drive.google.com/drive/folders/1KFxqi0rO-bJrd03rLk87fF1iOmnjpaoG),&#xD;
with some preprocessing: Each pair of images (original and segmented), was separated into individual staffs and the symbol colors were negated (so that there would be more contrast with the black background).&#xD;
&#xD;
![SegNet architecture][4]&#xD;
&#xD;
![Segmented staff][5]&#xD;
![`Binarize@*Blur` of the segmented staff][6]&#xD;
&#xD;
## Finding the Bounding Boxes&#xD;
&#xD;
In order to find the bounding boxes from the segmented image, we look for the its morphological components using `ComponentMeasurements`.&#xD;
Before using `ComponentMeasurements`, we blur and binarize the segmented image, as it usually yields more accurate results; we also discard&#xD;
any bounding boxes with area less than 25 pixels, as that is very likely just noise.&#xD;
&#xD;
![Bounding boxes][7]&#xD;
&#xD;
# Classifying the Musical Components&#xD;
&#xD;
For the component classification, we use a `ClassifierFunction` trained on the DeepScores [^deepscores] [Classification Dataset](https://drive.google.com/file/d/1bdBrX0dAX734I3MA_6-wH_-N2eqq_tf_/view),&#xD;
cropping the images in relation to a lookup table - this is so that the images contain only the actual symbol, and the classifier doesn&amp;#039;t learn the context instead of the symbol.&#xD;
&#xD;
Unfortunately, the classifier trained during the Wolfram Summer Program misclassifies some images; however, it does still provide something that can be worked with.&#xD;
&#xD;
![Classified symbols][8]&#xD;
&#xD;
# Parsing the Sheet Music&#xD;
&#xD;
Very limited parsing could be done during the Wolfram Summer Program: we sort the notes and pitch them, and add rests in as well.&#xD;
&#xD;
## Finding the Pitches&#xD;
&#xD;
Pitching the notes depends on their distance to the bottom of the staff and a reference pitch, which is determined by the clef. Because of the way we trimmed the staff images,&#xD;
we know that the first staff line (from the bottom) has the Y coordinate $2.25 \Delta$, where $\Delta$ is the distance between the staff lines in the original image.&#xD;
We also know, from the way we trimmed the staffs from the original page, that the distance between the staff lines in the resized image is fixed - and is $\delta = 10$.&#xD;
&#xD;
`PitchNumber` calculates the distance from the note centroid to the bottom of the staff, normalizing by half of the distance between the staff lines.&#xD;
`PitchToLetter` finds the name for the given output of `PitchNumber` in relation to some reference pitch.&#xD;
&#xD;
![Centroids of the correctly-classified notes][9]&#xD;
&#xD;
```&#xD;
PitchNumber[noteCentroid_, \[Delta]_, bottom_] := (noteCentroid[[2]] - bottom)/(0.5 \[Delta])&#xD;
&#xD;
naturalNotes =&#xD;
  Flatten[Table[# &amp;lt;&amp;gt; ToString[i] &amp;amp; /@ {&amp;#034;A&amp;#034;, &amp;#034;B&amp;#034;, &amp;#034;C&amp;#034;, &amp;#034;D&amp;#034;, &amp;#034;E&amp;#034;, &amp;#034;F&amp;#034;, &amp;#034;G&amp;#034;}, {i, 1, 7}], 1]&#xD;
&#xD;
PitchToLetter[pitchNumber_, referenceNumber_, referenceLetter_] :=&#xD;
 RotateLeft[naturalNotes,&#xD;
   FirstPosition[naturalNotes, referenceLetter] - 1][[&#xD;
  Round[pitchNumber - referenceNumber] + 1]]&#xD;
```&#xD;
&#xD;
## Basic Parsing&#xD;
&#xD;
In this case, the parsing is a simple sorting - there are no dynamics, articulation or even accidentals taken into consideration.&#xD;
&#xD;
```&#xD;
ParseSheetMusic[pitchedNotes_, rests_] :=&#xD;
 SortBy[Join[pitchedNotes, restsNotation], NotationCentroid[#][[1]] &amp;amp;]&#xD;
```&#xD;
&#xD;
In the end, this is our final result:&#xD;
&#xD;
```&#xD;
{SheetMusicNote[{66.5, 64.}, &amp;#034;B5&amp;#034;],&#xD;
 SheetMusicRest[{97., 45.5}, &amp;#034;restHBar&amp;#034;],&#xD;
 SheetMusicRest[{97.5, 64.5}, &amp;#034;restHalf&amp;#034;],&#xD;
 SheetMusicNote[{121., 64.}, &amp;#034;B5&amp;#034;],&#xD;
 SheetMusicNote[{159., 64.}, &amp;#034;B5&amp;#034;],&#xD;
 SheetMusicNote[{196.5, 64.}, &amp;#034;B5&amp;#034;],&#xD;
 SheetMusicRest[{287., 49.5}, &amp;#034;rest32nd&amp;#034;],&#xD;
 SheetMusicNote[{327.5, 50.}, &amp;#034;F4&amp;#034;],&#xD;
 SheetMusicNote[{366., 59.5}, &amp;#034;A5&amp;#034;],&#xD;
 SheetMusicRest[{456., 75.}, &amp;#034;restQuarter&amp;#034;]}&#xD;
```&#xD;
&#xD;
[^segnet]: [https://arxiv.org/abs/1511.00561](https://arxiv.org/abs/1511.00561)&#xD;
[^deepscores]: [https://tuggeluk.github.io/papers/preprint_deepscores.pdf](https://tuggeluk.github.io/papers/preprint_deepscores.pdf)&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=original-sheet.png&amp;amp;userId=1726262&#xD;
  [2]: https://community.wolfram.com//c/portal/getImageAttachment?filename=original-staff.png&amp;amp;userId=1726262&#xD;
  [3]: https://community.wolfram.com//c/portal/getImageAttachment?filename=nostaffs.png&amp;amp;userId=1726262&#xD;
  [4]: https://community.wolfram.com//c/portal/getImageAttachment?filename=segnet-architecture.png&amp;amp;userId=1726262&#xD;
  [5]: https://community.wolfram.com//c/portal/getImageAttachment?filename=segmented.png&amp;amp;userId=1726262&#xD;
  [6]: https://community.wolfram.com//c/portal/getImageAttachment?filename=binblur.png&amp;amp;userId=1726262&#xD;
  [7]: https://community.wolfram.com//c/portal/getImageAttachment?filename=bboxes.png&amp;amp;userId=1726262&#xD;
  [8]: https://community.wolfram.com//c/portal/getImageAttachment?filename=classified.png&amp;amp;userId=1726262&#xD;
  [9]: https://community.wolfram.com//c/portal/getImageAttachment?filename=notes.png&amp;amp;userId=1726262</description>
    <dc:creator>Daniel Csillag</dc:creator>
    <dc:date>2019-07-10T20:35:05Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/3062832">
    <title>The Telephone Game - next level with GPT</title>
    <link>https://community.wolfram.com/groups/-/m/t/3062832</link>
    <description>![enter image description here][1]&#xD;
&#xD;
&amp;amp;[Wolfram Notebook][2]&#xD;
&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=w5qgsdf.jpg&amp;amp;userId=11733&#xD;
  [2]: https://www.wolframcloud.com/obj/04458d24-aacf-4cd7-8a5d-46efde37e927</description>
    <dc:creator>Marco Thiel</dc:creator>
    <dc:date>2023-11-09T22:51:38Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1380021">
    <title>[WSS18] Generating Music with Expressive Timing and Dynamics</title>
    <link>https://community.wolfram.com/groups/-/m/t/1380021</link>
    <description>![Cover][1]&#xD;
&#xD;
## Goal ##&#xD;
There are many ways to generate music and one of them is algorithmic, where music is generated with the help of a list of handcrafted rules.    &#xD;
&#xD;
The approach in this project is different - I build a neural network that knows nothing about music but learns it from thousands of songs given in MIDI format.&#xD;
    &#xD;
_Apart from just generating a meaningful sequence of notes I also wanted to add **dynamics** in loudness and humanlike mistakes in timing with **no restrictions for note durations**._&#xD;
&#xD;
 - **Why dynamics and timing?**  &#xD;
There is no human who is able to play on a musical instrument with precisely the same loudness and strictly in time with a metronome(at least I can&amp;#039;t). People do mistakes, but in the case of music, they are helping in creating what we call more alive music. It is a fact that dynamic music with slight time shifts sounds more interesting, so even when you write music in a program you supposed to add these &amp;#034;mistakes&amp;#034; by yourself.&#xD;
&#xD;
  - **Why performances?**  &#xD;
The dataset that I use for the project contains performances of [Yamaha e-piano competition][2] participants. This gives us a possibility to learn the dynamics and mistakes in timings.&#xD;
&#xD;
__Here&amp;#039;s an [example][3] generated by the model.__&#xD;
&#xD;
All the code, data and trained models can be found on [GitHub][32]. &#xD;
&#xD;
The examples will be attached to this post as files just in case.&#xD;
&#xD;
----------&#xD;
## Inspiration ##&#xD;
This is not an original work and mostly it&amp;#039;s an attempt to recreate the work of [Magenta][4] team from their blog [post][5]. &#xD;
&#xD;
Nevertheless, in this post, I will try to add more details to the **preprocessing** steps and how you can build a similar neural network model in Wolfram Language.&#xD;
&#xD;
## Data ##&#xD;
I&amp;#039;ve used a [site][6] that has the Yamaha e-piano performances but also contains a set of classic and jazz compositions.&#xD;
 &#xD;
In the original [work][7] Magenta team has used only the Yamaha dataset but with a heavy augmentation on top of that: Time-stretching (making each performance up to 5% faster or slower), Transposition (raising or lowering the pitch of each performance by up to a major third).&#xD;
&#xD;
Also, you can create your own list of MIDI files and build a dataset with the help of the code provided below in the post.    &#xD;
Here are links to find a lot of free MIDI songs: [The Lakh MIDI Dataset][8](very well prepared a dataset for ML projects), [MidiWorld][9] and [FreeMidi][10]&#xD;
&#xD;
## MIDI ##&#xD;
MIDI is short for Musical Instrument Digital Interface. Its a language that allows computers, musical instruments, and other hardware to communicate.&#xD;
MIDI carries event messages that specify musical notation, pitch, velocity, vibrato, panning, and clock signals (which set tempo).&#xD;
&#xD;
_For the project, we need only events that denote where is every note starts/ends and with what are velocity and pitch._&#xD;
&#xD;
## Preprocessing The Data ##&#xD;
Even though MIDI is already a digital representation of music, we can&amp;#039;t just take raw bytes of a file and feed it to an ML model as in the case of the models working with images. First of all, images and music are conceptually different tasks: the first is a single event(data) per item(an image), the second is a sequence of events per item(a song). Another reason is that raw MIDI representation and a single MIDI event itself contain a lot of irrelevant information to our task.&#xD;
&#xD;
Thus we need a special data representation, a MIDI-like stream of musical events. Specifically, I use the following set of events:&#xD;
&#xD;
- 88 **note-on** events, one for each of the 88 MIDI pitches of piano range. These events start a new note.&#xD;
- 88 **note-off** events, one for each of the 88 MIDI pitches of piano range. These events release a note.&#xD;
- 100 **time-shift** events in increments of 10 ms up to 1 second. These events move forward in time to the next note event.&#xD;
- 34 **velocity** events, corresponding to MIDI velocities quantized into 32 bins. These events change the velocity applied to subsequent notes.&#xD;
&#xD;
The neural network operates on a one-hot encoding over these 310 different events. This is the very same representation as in the original work but the number of note-on/note-off is fewer, I encode 88 notes in piano range instead of 127 notes in MIDI pitch range to reduce one-hot encoding vector size and make the process of learning easier.&#xD;
&#xD;
**For example**, if you want to encode 4 notes from C major with durations of a half second and with different velocities your sequence of events would be somewhat like this(for clarity I use only indices instead of the whole one-hot encoding):    &#xD;
&#xD;
`{288, 60, 226, 148, 277,  62, 226, 150, 300, 64, 226, 152, 310, 67, 226, 155}`&#xD;
![Preprocessing encoding C major example][11]&#xD;
&#xD;
In this particular example:    &#xD;
- _60, 62, 64, 67_ are **note on** events(C5,  D5, E5, G5). Values in a range from 1 to 88.    &#xD;
- _148, 150, 152, 155_ are **note off** events. Values in a range from 89 to 176.    &#xD;
- _226_ is a half second **time shift** event. Values in a range from 177 = 10 ms to 276 = 1 sec.  &#xD;
- _288, 277, 300, 310_ are **velocity** events. Values in a range from 277 to 310.&#xD;
&#xD;
In this way, you can encode music that is expressive in dynamics and timing.    &#xD;
Now, let&amp;#039;s take a look on another example with a chord from the same notes but with different durations:&#xD;
&#xD;
`{300, 60, 62, 64, 67, 226, 152, 155, 226, 150, 226, 148}`&#xD;
![C major chord][12]    &#xD;
As you can see, if you want to play more than one note at once you just need to put them in a single bunch of note-on events(60, 62, 64, 67).    &#xD;
Then you add time shift and note-off events as you needed. If you need a duration longer than 1 sec you can stack together more than one time-shift events({310, 310} = 2 sec time-shift).&#xD;
&#xD;
**WL and MIDI**&#xD;
&#xD;
Wolfram Language has a **built-in** support of MIDI files what is really simplifying initial work.    &#xD;
To get data from MIDI file you need to import it with specific elements:&#xD;
![WL MIDI Import Elements][13]    &#xD;
In the code below I also extract and calculate needed information related to a tempo of a song.&#xD;
&#xD;
	{raw, header} = Import[path, #]&amp;amp; /@ {&amp;#034;RawData&amp;#034;, &amp;#034;Header&amp;#034;};&#xD;
&#xD;
	tempos = Cases[Flatten[raw], HoldPattern[&amp;#034;SetTempo&amp;#034; -&amp;gt; tempo_] :&amp;gt; tempo];&#xD;
&#xD;
	microsecondsPerBeat = If[Length@tempos &amp;gt; 0, First[tempos], 500000]; (* If there is no explicit tempo we use default 120 bpm *)&#xD;
	&#xD;
	timeDivision = First@Cases[header, HoldPattern[&amp;#034;TimeDivision&amp;#034; -&amp;gt; division_] :&amp;gt; division];&#xD;
    (* Convert timeDivision value to base of 2 *)&#xD;
	timeDivisionBits = IntegerDigits[timeDivision, 2];&#xD;
    (* Pad zeros at the beginning if the value takes less then 16 bits *)&#xD;
	timeDivisionBits = If[Length@timeDivisionBits &amp;lt; 16, PadLeft[timeDivisionBits, 16], timeDivisionBits]; &#xD;
    (* The top bit responsible for the type of TimeDivision *)&#xD;
	timeDivisionType = timeDivisionBits[[1]];&#xD;
	framesPerSecond = timeDivisionBits[[2 ;; 8]];&#xD;
	ticksPerFrame = timeDivisionBits[[9 ;; 16]];&#xD;
	&#xD;
	ticksPerBeat = If[timeDivisionType == 0, timeDivision, 10^6 /(framesPerSecond * ticksPerFrame)];&#xD;
	&#xD;
	secondsPerTick = (microsecondsPerBeat / ticksPerBeat) * 10^-6.;&#xD;
&#xD;
An example of raw data and header info from MIDI file in Wolfram Language:    &#xD;
![Raw MIDI output][14]    &#xD;
**SetTempo** is a number of microseconds per beat(microseconds per quarter note).    &#xD;
**Time Division** has two type of interpreting. If the top bit is 0 then the type is &amp;#034;ticks per beat&amp;#034; (or pulses per quarter note) otherwise, the type is &amp;#034;frames per second&amp;#034;. We need those two values to calculate time per one **MIDI tick** that used in MIDI events as a time measurement. &#xD;
&#xD;
One MIDI event in WL representation looks like this&#xD;
&#xD;
`{56, {9, 0}, {46, 83}}`&#xD;
&#xD;
- 56 is a number of **MIDI ticks** that means the total amount of time that must pass from the previous MIDI event.    &#xD;
It represents our **time-shift** event by simple multiplication of this number with **secondsPerTick**.&#xD;
- 9 is a status byte of MIDI events(9,8 are **note-on**, **note-off** respectively).&#xD;
- 0 is MIDI channel(irrelevant for us).&#xD;
- 46 indicates what is a pitch of this note(related to **note-on**/**note-off** events).&#xD;
- 83 is a number we encode in a **velocity** event.&#xD;
&#xD;
If you want to understand how a real raw MIDI data structured, this [blog][15] is specifically useful.&#xD;
&#xD;
Now, what we need is to parse a sequence of MIDI events and filter them only for events that are **note-on**, **note-off** and all the events that have the number of **MIDI ticks** greater than 0. Some of the meta-messages have irrelevant MIDI ticks thus we need to exclude them from final sequence - we just skip the events with value **F**(Meta message) in the MIDI status byte.&#xD;
&#xD;
After filtering MIDI data you get a sequence that is ready to be encoded to the final representation and will be fed to the model.&#xD;
![Filtered MIDI events][16]    &#xD;
&#xD;
To encode the sequence of MIDI events to the final representation I use the code below:&#xD;
&#xD;
    EncodeMidi[track_, secondsPerTick_] := Block[{lastVelocity = 0},&#xD;
      ClearAll[list];&#xD;
      Flatten[&#xD;
        Map[&#xD;
          Block[{list = {}},&#xD;
          (* Add time shifts when needed *)&#xD;
            If[TimeShiftByte[#, secondsPerTick] &amp;gt; 0, list = Join[list, EncodeTimeShift[TimeShiftByte[#, secondsPerTick]]]];&#xD;
    &#xD;
            (* Proceed with logic only if it&amp;#039;s a note event *)&#xD;
            If[StatusByte[#] == NoteOnByte || StatusByte[#] == NoteOffByte,&#xD;
    &#xD;
            (* Add velocity if it&amp;#039;s different from the last seen *)&#xD;
              If[lastVelocity != QuantizedVelocity[VelocityByte[#]] &amp;amp;&amp;amp; StatusByte[#] == NoteOnByte,&#xD;
    &#xD;
                lastVelocity = QuantizedVelocity[VelocityByte[#]];&#xD;
                list = Join[list, List[EncodeVelocity[VelocityByte[#]]]];&#xD;
              ];&#xD;
    &#xD;
              (* Add note event *)&#xD;
              list = Join[list, List[EncodeNote[NoteByte[#], StatusByte[#] == NoteOnByte]]];&#xD;
            ];&#xD;
    &#xD;
            (* Return encoded list*)&#xD;
            list&#xD;
          ]&amp;amp;,&#xD;
          track]&#xD;
        , 1]];&#xD;
&#xD;
This code has a lot of functions that I&amp;#039;ve written during the summer school but they are mostly utility short functions.&#xD;
You can check them and complete implementation on [GitHub][17].    &#xD;
&#xD;
When the code for the preprocessing is ready it&amp;#039;s time to build a dataset.&#xD;
&#xD;
**Building Dataset**&#xD;
&#xD;
I&amp;#039;ve made a [notebook][18] that takes care of preprocessing of MIDI files and encode them into the final representation.&#xD;
&#xD;
    (* Take all files names in Midi folder *)&#xD;
    files = FileNames[&amp;#034;*&amp;#034;, NotebookDirectory[] &amp;lt;&amp;gt; &amp;#034;Midi&amp;#034;];&#xD;
    dataset = Flatten[EncodeTrack /@ files, 1];&#xD;
&#xD;
During the encoding, each track is partitioning into smaller segments:&#xD;
&#xD;
    encodings = Partition[EncodeMidi[GetMidiEvents[raw, secondsPerTick], secondsPerTick], 500];&#xD;
&#xD;
In the original work, Magenta team split each song into 30-second segments to keep each example of manageable size. The problem is that partition by equal time doesn&amp;#039;t give you the equal size of examples. Even though you can use varying input size in sequence models I wanted to use a static size of examples to speed up the training process. I was told that internally in WL(or maybe everywhere) it&amp;#039;s more efficient to have the same size of every example for a model.    &#xD;
However, I believe this kind of partition has a drawback, in a way that an equal number of encoded events could have a different duration in time thus adding inconsistency in the dataset.&#xD;
&#xD;
In my case, I&amp;#039;ve divided each song into segments of 500 encoded events.&#xD;
![One Song Final Encoding][19]    &#xD;
To reduce the size of the final dataset I use only indices for one-hot encodings.    &#xD;
As the result, the final dimension of my dataset was **{99285, 500}**&#xD;
&#xD;
If you want to try partition by the time you need to edit `EncodeTrack` function in [`Midi.m`][20].    &#xD;
With this code, you will find positions of where to split a sequence on equal time segments:&#xD;
&#xD;
    GetTimePositions[track_, seconds_, secondsPerTick_] := &#xD;
     Block[{positions = {}, time = 0},&#xD;
      Do[&#xD;
       time = time + track[[i]][[1]] * secondsPerTick;&#xD;
       If[time &amp;gt; seconds, positions = Append[positions, i]; time = 0;],&#xD;
       {i, Length@track}];&#xD;
      positions&#xD;
      ]&#xD;
&#xD;
Where parameter `track` is a sequence of MIDI events. Then you split the same `track` with the positions you&amp;#039;ve got from the function.&#xD;
&#xD;
    segments = FoldPairList[TakeDrop, track, positions];&#xD;
&#xD;
After that, you need to encode `segments` with the help of `EncodeMidi` function. If you do that there is one thing left - rework the model to accept varying input size but the next part will cover how to build a model with a static size of example.&#xD;
&#xD;
----------&#xD;
&#xD;
## Building a Model ##&#xD;
Because music data is a sequence of events we need an architecture that knows how to remember, and predicts what is the next event based on all previous. This is exactly what Recurrent Neural Networks try to do - RNNs can use their internal state (memory) to process sequences of inputs. If you want to check more details I would recommend to watch this [introduction][21] video.&#xD;
&#xD;
On the abstract level, RNN learns the probabilities of events that follow after each other. Take for example this language model from Wolfram Neural Repository, it predicts the next character of a given sequence.&#xD;
&#xD;
    NetModel[&amp;#034;Wolfram English Character-Level Language Model V1&amp;#034;][&amp;#034;hello worl&amp;#034;]&#xD;
&#xD;
The output is **d**.&#xD;
&#xD;
You can get top 5 probabilities if you want.&#xD;
&#xD;
    NetModel[&amp;#034;Wolfram English Character-Level Language Model V1&amp;#034;][&amp;#034;hello worl&amp;#034;, {&amp;#034;TopProbabilities&amp;#034;, 5}]&#xD;
You will get:&#xD;
&#xD;
    {&amp;#034;d&amp;#034; -&amp;gt; 0.980898, &amp;#034;e&amp;#034; -&amp;gt; 0.00808785, &amp;#034;h&amp;#034; -&amp;gt; 0.0045687,  &amp;#034; &amp;#034; -&amp;gt; 0.00143807, &amp;#034;l&amp;#034; -&amp;gt; 0.000681855}&#xD;
&#xD;
In my work, I needed similar behavior but instead of characters, I wanted to predict encoded MIDI events. That is why the basis of the model I build is [Wolfram English Character-Level Language Model V1][22]. Also, after reading a [guide][23] about sequence learning with neural networks in WL I&amp;#039;ve decided to improve the training process with &amp;#034;teacher forcing&amp;#034; technique.&#xD;
&#xD;
**Teacher Forcing**&#xD;
&#xD;
In a simple language model, a model takes the last prediction from an input sequence and compute the class of it. But for &amp;#034;teacher forcing&amp;#034; we need to get classes of all predictions.&#xD;
&#xD;
![Model comparison][24]&#xD;
&#xD;
Comparatively to the language model I&amp;#039;ve removed one `GatedReccurentLayer` and `Dropoutlayer` due to the not so big dataset(as precautions to avoid overfitting). Another benefit of using &amp;#034;teacher forcing&amp;#034; is that you don&amp;#039;t need to separately create labels for every example. To compute the loss we make out of an input example two sequences:&#xD;
&#xD;
1. Everything but the **last** element(Sequence**Most**Layer)&#xD;
2. Everything but the **first** element(Sequence**Rest**Layer)&#xD;
&#xD;
![Teacher Forcing Net][25]&#xD;
&#xD;
As you can notice the input is only one vector of indices with size 500 and labels for computing the loss are generating inside of a `NetGraph`.&#xD;
Here is a visualized example of the flow with simple input:&#xD;
&#xD;
![Input flow explanation][26]&#xD;
&#xD;
You can find the code for creating the model in this [PerfrormanceRnnModel][27] notebook. &#xD;
After all the data is ready and the model is finalized we can start training.&#xD;
&#xD;
    NetTrain[teacherForcingNet, &#xD;
     	&amp;lt;|&amp;#034;Input&amp;#034; -&amp;gt; dataTrain|&amp;gt;, &#xD;
     	All, &#xD;
     	TrainingProgressCheckpointing -&amp;gt; {&amp;#034;File&amp;#034;,  checkPointDir,  &amp;#034;Interval&amp;#034; -&amp;gt; Quantity[5, &amp;#034;Minutes&amp;#034;]},&#xD;
     	BatchSize -&amp;gt; 64, &#xD;
     	MaxTrainingRounds -&amp;gt; 10,&#xD;
     	TargetDevice -&amp;gt; &amp;#034;GPU&amp;#034;,  (* Use CPU if you don&amp;#039;t have Nvidia GPU *)&#xD;
     	ValidationSet -&amp;gt; &amp;lt;|&amp;#034;Input&amp;#034; -&amp;gt; dataValidate|&amp;gt;&#xD;
     ]&#xD;
A friendly advice - it&amp;#039;s better to use **&amp;#034;Checkpoining&amp;#034;** during the training. This will keep your mental health safe and will work as assurance that all training progress is saved.&#xD;
&#xD;
I was training the model 30 rounds and it took around 4-5 hours on AWS&amp;#039; GPUs.&#xD;
First 10-15 rounds weren&amp;#039;t showing any sight of problems but later training clearly started to overfit.&#xD;
![Training loss][28]&#xD;
&#xD;
Unfortunately, I haven&amp;#039;t had time to fix this problem because of the limited time but to overcome this problem I might reduce the size of GRUs from 512 to 256 and return Dropout layer.&#xD;
&#xD;
## Generate Music ##&#xD;
To generate music we need a model that predicts the next event in a sequence as it was in the language model. To do that I take the trained model and extract out of it &amp;#034;PerformanceRNN Predict Model&amp;#034; part.&#xD;
&#xD;
    predictNet = NetExtract[trainedNet, &amp;#034;predict&amp;#034;];&#xD;
&#xD;
Next step is to convert this `predictNet` to a model that takes varying input size and return the class of the next event.&#xD;
&#xD;
    generateModel = NetJoin[NetTake[predictNet, 3], {&#xD;
      SequenceLastLayer[],&#xD;
      NetExtract[predictNet, {4, &amp;#034;Net&amp;#034;}],&#xD;
      SoftmaxLayer[]},&#xD;
     &amp;#034;Input&amp;#034; -&amp;gt;  Automatic,&#xD;
     &amp;#034;Output&amp;#034; -&amp;gt; NetDecoder[{&amp;#034;Class&amp;#034;, Range[310]}]&#xD;
     ]&#xD;
&#xD;
The resulting architecture is pretty the same as the language model from which I&amp;#039;ve started - it takes a sequence with varying size of encoded MIDI events `{177, 60, 90}` and predicts what could be next event `{177, 60, 90, ?}`.&#xD;
&#xD;
![Model Comparison(Generation)][29]&#xD;
&#xD;
**Now, let&amp;#039;s the fun begin!**&#xD;
&#xD;
    generateDemo[net_, start_, len_] :=  Block[{obj = NetStateObject[net]}, &#xD;
     Join@NestList[{obj[#, &amp;#034;RandomSample&amp;#034;]} &amp;amp;, start, len]&#xD;
    ]&#xD;
&#xD;
This small function is all we need to generate a sequence of the desired length.    &#xD;
&#xD;
`NetStateObject` helps to keep track of all sequences that were applied to the network, meaning every next prediction is the result of all previous events not only the recent one.&#xD;
&#xD;
`start` should be a sequence of encoded MIDI events. It also can be a single item sequence, say you want to start from a pause or a particular note. This is a possibility to some extent put the generation process in a particular direction.&#xD;
&#xD;
Okay, two lines of code left and you can hear play with generating of music:&#xD;
&#xD;
    generatedSequence = Flatten[generateDemo[generateModel,  {60, 216, 148,  62, 200, 150, 64, 236, 152, 67, 198, 155}, 500]];&#xD;
    ToSound[generatedSequence]&#xD;
&#xD;
These are other examples: [2][30], [3][31].    &#xD;
You can generate your own demos if download [repository][32] and open [PerformanceRNN][33] notebook.&#xD;
&#xD;
## Further Work ##&#xD;
That was a very fun and challenging task for me. I can&amp;#039;t say that I&amp;#039;m satisfied with the results but this a good start and I have a direction now.&#xD;
What I want to explore is Variational Autoencoder, especially [MusicVAE][34] that is made by the same Magenta team.&#xD;
&#xD;
However, I&amp;#039;ll start with improving the existing model by changing the architecture and cleaning the dataset to have only performances from the Yamaha dataset.&#xD;
&#xD;
Thank you for reading the post, and feel free to ask any questions.&#xD;
&#xD;
![Peace!][35]&#xD;
&#xD;
&#xD;
  [1]: http://community.wolfram.com//c/portal/getImageAttachment?filename=2433article_cover.png&amp;amp;userId=1352227&#xD;
  [2]: http://www.piano-e-competition.com&#xD;
  [3]: https://drive.google.com/open?id=1I7l6hrecWsuMxqvEdUiRWtg6N6NCW34R&#xD;
  [4]: https://magenta.tensorflow.org/&#xD;
  [5]: https://magenta.tensorflow.org/performance-rnn&#xD;
  [6]: http://www.kuhmann.com/Yamaha.htm&#xD;
  [7]: https://github.com/tensorflow/magenta/tree/master/magenta/models/performance_rnn&#xD;
  [8]: http://colinraffel.com/projects/lmd/&#xD;
  [9]: http://www.midiworld.com/&#xD;
  [10]: https://freemidi.org/&#xD;
  [11]: http://community.wolfram.com//c/portal/getImageAttachment?filename=5707Preprocessing_explanation.png&amp;amp;userId=1352227&#xD;
  [12]: http://community.wolfram.com//c/portal/getImageAttachment?filename=6109Prep_ex_2.png&amp;amp;userId=1352227&#xD;
  [13]: http://community.wolfram.com//c/portal/getImageAttachment?filename=MIDIimportelements.png&amp;amp;userId=1352227&#xD;
  [14]: http://community.wolfram.com//c/portal/getImageAttachment?filename=7717raw_midi_output.png&amp;amp;userId=1352227&#xD;
  [15]: http://www.recordingblogs.com/wiki/musical-instrument-digital-interface-midi&#xD;
  [16]: http://community.wolfram.com//c/portal/getImageAttachment?filename=filtered_midi_events.png&amp;amp;userId=1352227&#xD;
  [17]: https://github.com/Apisov/Performance-RNN-WL/blob/master/Project/Midi.m&#xD;
  [18]: https://github.com/Apisov/Performance-RNN-WL/blob/master/BuildData.nb&#xD;
  [19]: http://community.wolfram.com//c/portal/getImageAttachment?filename=One_track_final_encoding.png&amp;amp;userId=1352227&#xD;
  [20]: https://github.com/Apisov/Performance-RNN-WL/blob/master/Project/Midi.m&#xD;
  [21]: http://www.wolfram.com/wolfram-u/catalog/wl036/&#xD;
  [22]: https://resources.wolframcloud.com/NeuralNetRepository/resources/Wolfram-English-Character-Level-Language-Model-V1&#xD;
  [23]: http://reference.wolfram.com/language/tutorial/NeuralNetworksSequenceLearning.html#1013067167&#xD;
  [24]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Modelcomparison.png&amp;amp;userId=1352227&#xD;
  [25]: http://community.wolfram.com//c/portal/getImageAttachment?filename=3750Teacher_forcing.png&amp;amp;userId=1352227&#xD;
  [26]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Teacher_forcing_explanation.png&amp;amp;userId=1352227&#xD;
  [27]: https://github.com/Apisov/Performance-RNN-WL/blob/master/PerformanceRNNModel.nb&#xD;
  [28]: http://community.wolfram.com//c/portal/getImageAttachment?filename=raw_midi.png&amp;amp;userId=1352227&#xD;
  [29]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Modelcomparison%28Generation%29.png&amp;amp;userId=1352227&#xD;
  [30]: https://drive.google.com/open?id=1GtlaOtTF_9rHiDVsrqmLnUaKCSAva1dP&#xD;
  [31]: https://drive.google.com/open?id=1sEihbFJw4XbVZveYl8efoM8Ivq8781ar&#xD;
  [32]: https://github.com/Apisov/Performance-RNN-WL&#xD;
  [33]: https://github.com/Apisov/Performance-RNN-WL/blob/master/PerformanceRNN.nb&#xD;
  [34]: https://magenta.tensorflow.org/music-vae&#xD;
  [35]: http://community.wolfram.com//c/portal/getImageAttachment?filename=d2eedc8a1ea8fc6a62e23b151c7fb3675c8153cc.png&amp;amp;userId=1352227</description>
    <dc:creator>Pavlo Apisov</dc:creator>
    <dc:date>2018-07-11T21:20:56Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1383518">
    <title>[WSC18] Music Sentiment Analysis through Machine Learning</title>
    <link>https://community.wolfram.com/groups/-/m/t/1383518</link>
    <description>![A Representation of the emotion categorization system][1]&#xD;
&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
#Abstract&#xD;
This project aims to develop a machine learning application to identify the sentiments in a music clip. The data set I used consists of one hundred 45-second clips from the Database for Emotional Analysis of Music and an additional 103 gathered by myself. I manually labeled all 203 clips and used them as training data for my program. This program works best with classical-style music, which is the main component of my data set, but also works with other genres to an reasonable extent. &#xD;
&#xD;
#Introduction&#xD;
One of the most important functions of music is to affect emotion, but the experience of emotion is ambiguous and subjective to individual. The same music may induce a diverse range of feelings in people as a result of different context, personality, or culture. Many musical features, however, usually lead to the same effect on the human brain. For example, louder music correlates more with excitement or anger, while softer music corresponds to tenderness. This consistency makes it possible to train a supervised machine learning program based on musical features.&#xD;
&#xD;
#Background&#xD;
This project is based on James Russell&amp;#039;s circumplex model, in which a two-dimensional emotion space is constructed from the x-axis of valence level and y-axis of arousal level, as shown above in the picture. Specifically, valence is a measurement of an emotion&amp;#039;s pleasantness, whereas arousal is a measurement of an emotion&amp;#039;s intensity. Russell&amp;#039;s model provides a metric on which different sentiments can be compared and contrasted, creating four main categories of emotion: Happy (high valence, high arousal), Stressed (low valence, high arousal), Sad (low valence, low arousal), and Calm (high valence, low arousal). Within these main categories there are various sub-categories, labeled on the graph above. Notably, &amp;#034;passionate&amp;#034; is a sub-category that does not belong to any main category due to its ambiguous valence value. &#xD;
&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
#Program Structure&#xD;
The program contains a three-layer structure. The first layer is responsible for extracting musical features, the second for generating a list of numerical predictions based on different features, and the third for predicting and displaying the most probable emotion descriptors based on the second layer&amp;#039;s output.  &#xD;
![enter image description here][2]&#xD;
&#xD;
##First Layer&#xD;
&#xD;
The first layer consists of 23 feature extractors that generate numerical sequence based on different features:&#xD;
&#xD;
    (*A list of feature extractors*)&#xD;
    feMin[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Min&amp;#034;, List]]&#xD;
    feMax[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Max&amp;#034;, List]]&#xD;
    feMean[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Mean&amp;#034;, List]]&#xD;
    feMedian[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Median&amp;#034;, List]]&#xD;
    fePower[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Power&amp;#034;, List]]&#xD;
    feRMSA[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;RMSAmplitude&amp;#034;, List]]&#xD;
    feLoud[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Loudness&amp;#034;, List]]&#xD;
    feCrest[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;CrestFactor&amp;#034;, List]]&#xD;
    feEntropy[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Entropy&amp;#034;, List]]&#xD;
    fePeak[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;PeakToAveragePowerRatio&amp;#034;, List]]&#xD;
    feTCent[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;TemporalCentroid&amp;#034;, List]]&#xD;
    feZeroR[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;ZeroCrossingRate&amp;#034;, List]]&#xD;
    feForm[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Formants&amp;#034;, List]]&#xD;
    feHighFC[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;HighFrequencyContent&amp;#034;, List]]&#xD;
    feMFCC[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;MFCC&amp;#034;, List]]&#xD;
    feSCent[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralCentroid&amp;#034;, List]]&#xD;
    feSCrest[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralCrest&amp;#034;, List]]&#xD;
    feSFlat[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralFlatness&amp;#034;, List]]&#xD;
    feSKurt[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralKurtosis&amp;#034;, List]]&#xD;
    feSRoll[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralRollOff&amp;#034;, List]]&#xD;
    feSSkew[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralSkewness&amp;#034;, List]]&#xD;
    feSSlope[audio_] :=  Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralSlope&amp;#034;, List]]&#xD;
    feSSpread[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;SpectralSpread&amp;#034;, List]]&#xD;
    feNovelty[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;Novelty&amp;#034;, List]]&#xD;
&amp;lt;br/&amp;gt;&#xD;
##Second Layer&#xD;
Using data generated from the first layer, the valence and arousal predictors of the second layer provide 46 predictions for the audio input, based on its different features. &#xD;
&#xD;
    (*RMSAmplitude*)&#xD;
    (*Feature extractor*) feRMSA[audio_] := Normal[AudioLocalMeasurements[audio, &amp;#034;RMSAmplitude&amp;#034;, List]]&#xD;
    dataRMSA = Table[First[takeLast[feRMSA[First[Take[musicFiles, {n}]]]]], {n, Length[musicFiles]}];&#xD;
    (*Generating predictor*) pArousalRMSA = Predict[dataRMSA -&amp;gt; arousalValueC]&#xD;
![Sample predictor function][3]&#xD;
&#xD;
&amp;lt;br/&amp;gt;&#xD;
##Third Layer&#xD;
The two parts of the third layer, main category classifier and sub-category classifier, each utilize the tensors generated in the second layer to make a prediction within their realm of emotion. The output consists of two parts, a main category emotion and a sub-category emotion.&#xD;
&#xD;
    (*Main*) emotionClassify1 = Classify[classifyMaterial -&amp;gt; emotionList1, PerformanceGoal -&amp;gt; &amp;#034;Quality&amp;#034;]&#xD;
    (*Sub*) emotionClassify2 = Classify[classifyMaterial -&amp;gt; emotionList2, PerformanceGoal -&amp;gt; &amp;#034;Quality&amp;#034;]&#xD;
![enter image description here][4]&#xD;
&#xD;
&amp;lt;br/&amp;gt;&#xD;
##Output&#xD;
If the program receives an input that is longer than 45 second, it will automatically clip the audio file into 45 second segments and return the result for each. If the last segment is less than 45 seconds, the program would still work fine on it, though with reduced accuracy. The display for each clip includes a main-category and a sub-category descriptor, with each of their associated probability also printed. &#xD;
&#xD;
###Sample testing: Debussy&amp;#039;s Clair de Lune&#xD;
![enter image description here][5]&#xD;
&#xD;
&amp;lt;br/&amp;gt;&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
#Conclusion&#xD;
The program gives very reasonable result for most music in the classical style. However, the program have three shortcomings that I plan to fix in later versions of the this program. Firstly, the program may give contradictory result (ex. happy and depressed) if the sentiment dramatically changes in the middle of a 45 second segment, perhaps reflecting the music&amp;#039;s changing emotional composition. The current 45 second clipping window is rather long and thus prone to capture contradicting emotions. In the next version of this program, the window will probably be shortened to 30 or 20 seconds to reduce prediction uncertainty. Secondly, the program&amp;#039;s processing speed has a lot of room of improvement. It currently takes about one and half minutes to compute an one minute audio file. In future versions I will remove relative ineffective feature extractors to speed things up. Lastly, the data used in creating this application is solely from myself, and therefore it is prone to my human biases. I plan to expand the data set with more people&amp;#039;s input and more genres of music. &#xD;
&#xD;
I have attached the application to this post so that everyone can try out the program.&#xD;
&#xD;
#Acknowledgement&#xD;
I sincerely thank my mentor, Professor Rob Morris, for providing invaluable guidance to help me carry out the project. I also want to thank Rick Hennigan for giving me crucial support with my code. &#xD;
&#xD;
&#xD;
  [1]: http://community.wolfram.com//c/portal/getImageAttachment?filename=8714Emotion2DSpace.PNG&amp;amp;userId=1371765&#xD;
  [2]: http://community.wolfram.com//c/portal/getImageAttachment?filename=2406DataStructure.PNG&amp;amp;userId=1371765&#xD;
  [3]: http://community.wolfram.com//c/portal/getImageAttachment?filename=8990capture1.PNG&amp;amp;userId=1371765&#xD;
  [4]: http://community.wolfram.com//c/portal/getImageAttachment?filename=5765capture2.PNG&amp;amp;userId=1371765&#xD;
  [5]: http://community.wolfram.com//c/portal/getImageAttachment?filename=3607SampleTesting.PNG&amp;amp;userId=1371765</description>
    <dc:creator>William Yicheng Zhu</dc:creator>
    <dc:date>2018-07-14T02:40:20Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2318363">
    <title>[WSC21] Analogues of the THX deep note chord</title>
    <link>https://community.wolfram.com/groups/-/m/t/2318363</link>
    <description>![Spectrogram of the THX sound recreation][1]&#xD;
&#xD;
&amp;amp;[Wolfram Notebook][2]&#xD;
&#xD;
  [Original Notebook]: https://www.wolframcloud.com/obj/be1a176a-f620-4a53-8f37-6c99bff8ad9e&#xD;
&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-07-15124908.png&amp;amp;userId=2316922&#xD;
  [2]: https://www.wolframcloud.com/obj/6d89e81f-272f-4a00-8996-1ebf68e128ac</description>
    <dc:creator>Evelyn Di Genova</dc:creator>
    <dc:date>2021-07-15T21:14:09Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/917048">
    <title>Hiding secret messages in music</title>
    <link>https://community.wolfram.com/groups/-/m/t/917048</link>
    <description>The [new computational audio features][1] of Mathematica are really impressive. In no time you can cook up things as soon as you understand the basic algorithm. Even the simplest tricks can give quite surprising results. Before you read on, please do play this (file also uploaded to this post):&#xD;
&#xD;
***[audio file][2]***.&#xD;
&#xD;
Have you noticed anything? I think that it sounds pretty much like the well known example &#xD;
&#xD;
    ExampleData[{&amp;#034;Sound&amp;#034;, &amp;#034;Apollo11SmallStep&amp;#034;}]&#xD;
&#xD;
As a matter of fact, it contains something a little special. If you import the file into Mathematica&#xD;
&#xD;
    secsound = Import[&amp;#034;/Users/thiel/Desktop/secretsound.wav&amp;#034;];&#xD;
&#xD;
and calculate a spectrogram of it&#xD;
&#xD;
    Spectrogram[secsound, ColorFunction -&amp;gt; &amp;#034;Rainbow&amp;#034;, Frame -&amp;gt; None, ImageSize -&amp;gt; Full]&#xD;
&#xD;
you get this:&#xD;
&#xD;
![enter image description here][3]&#xD;
&#xD;
How to inject images into spectrograms&#xD;
---------------------------&#xD;
&#xD;
I will show now, how you can get this in a couple of lines of code. First we need to get a binary matrix (later we can do better!) of the message. This is quite straight forward:&#xD;
&#xD;
    imgdata = Reverse@ImageData[ColorNegate@Image[Binarize[Rasterize[Text[&amp;#034;  Wolfram  &amp;#034;], RasterSize -&amp;gt; 100, ImageSize -&amp;gt; 100]]]];&#xD;
&#xD;
There is nothing really tricky in here. The text is &amp;#034;Wolfram&amp;#034;, I rasterise the image and resize it. Then I binarise it. The ColorNegate is needed to exchange ones and zeros in the matrix. Because I play with images and matrices, and they have a different coordinate system (the origin is at different corners) I need to Reverse the whole thing. I can plot the result like so:&#xD;
&#xD;
    ArrayPlot[Reverse@imgdata] &#xD;
&#xD;
![enter image description here][4]&#xD;
&#xD;
I now need to generate a sound that produces high amplitudes at the right places in the Spectrogram. At each and every place in the imagedata matrix that contains a one I need to proceed a little sine wave with the right frequency. The rows correspond to frequencies and the rows to time. So lets collect the different frequencies at each time:&#xD;
&#xD;
    list = Flatten[Position[#, 1]] &amp;amp; /@ Transpose[imgdata];&#xD;
&#xD;
Ok. Next we generate the corresponding sums of Sin-functions and generate a list of data from them. &#xD;
&#xD;
    listcompete = 0.1*Flatten[Table[Table[N@Total[Sin[2 Pi 300  # t] &amp;amp;@(# &amp;amp; /@ list)[[k]]], {t, 0, 8.71/200., 1/16000}], {k, 1, 100}], 1];&#xD;
&#xD;
 We can generate the corresponding sound:&#xD;
&#xD;
    Audio[Sound[SampledSoundList[listcompete, 8000]]]&#xD;
&#xD;
This gives you a little window like this&#xD;
&#xD;
![enter image description here][5]&#xD;
&#xD;
which allows you to &amp;#034;listen to Wolfram in dolphin language&amp;#034;. The file is attached to this post and sounds really cool. &#xD;
&#xD;
How to hide the images in sound files/music&#xD;
-------------------------------------------&#xD;
&#xD;
In order to hide the string in the &amp;#034;A small step ...&amp;#034; recording, we first shift the frequencies a little bit and decrease the amplitude:&#xD;
&#xD;
    listcompete2 = 0.02*Flatten[Table[Table[N@Total[Sin[2 Pi 1200  # t] &amp;amp;@(# &amp;amp; /@ list)[[k]]], {t, 0, 8.71/100., 1/64000}], {k, 1, 100}], 1];&#xD;
&#xD;
It looks now like this:&#xD;
&#xD;
    Spectrogram[Sound[SampledSoundList[listcompete2, 64000]], ColorFunction -&amp;gt; &amp;#034;Rainbow&amp;#034;]&#xD;
&#xD;
![enter image description here][6]&#xD;
&#xD;
If you want to listen to it use:&#xD;
&#xD;
    Audio[Sound[SampledSoundList[listcompete2, 64000]]]&#xD;
&#xD;
You should hear a sort of hissing sound. The new function AudioChannelCombine will now help us to merge the two sound objects:&#xD;
&#xD;
    AudioChannelCombine[{Audio[ExampleData[{&amp;#034;Sound&amp;#034;, &amp;#034;Apollo11SmallStep&amp;#034;}]], Audio[Sound[SampledSoundList[listcompete2, 64000]]]}]&#xD;
&#xD;
The resulting object is attached to this post. The spectrogram&#xD;
&#xD;
    Spectrogram[AudioChannelCombine[{Audio[ExampleData[{&amp;#034;Sound&amp;#034;, &amp;#034;Apollo11SmallStep&amp;#034;}]], &#xD;
    Audio[Sound[SampledSoundList[listcompete2, 64000]]]}], ColorFunction -&amp;gt; &amp;#034;Rainbow&amp;#034;, Frame -&amp;gt; None]&#xD;
&#xD;
![enter image description here][7]&#xD;
&#xD;
clearly shows the secret message blended into the Apollo message. &#xD;
&#xD;
Like this you can export the sound object:&#xD;
&#xD;
    secsound = Import[&amp;#034;/Users/thiel/Desktop/secretsound.wav&amp;#034;];&#xD;
&#xD;
Look for hidden messages&#xD;
------------------------&#xD;
&#xD;
This type of [procedure is quite well known][8]. I also saw it on [BBC&amp;#039;s Click][9], but I cannot remember the episode. Now you can use this to look for hidden messages in the internet or in music. Here are two examples: [file1][10] and [file2][11], both from the website above.&#xD;
&#xD;
Let&amp;#039;s look at file1&#xD;
&#xD;
    Spectrogram[snd, 150, Frame -&amp;gt; None]&#xD;
&#xD;
![enter image description here][12]&#xD;
&#xD;
and file2&#xD;
&#xD;
    Spectrogram[Import[&amp;#034;http://www.evansalazar.com/ohmpie/imageEncode/evan.mp3&amp;#034;], 150, Frame -&amp;gt; None, AspectRatio -&amp;gt; 1]&#xD;
&#xD;
![enter image description here][13]&#xD;
&#xD;
You can clearly see that the second image is actually &amp;#034;grayscale&amp;#034;. It is quite possible to achieve this by not Binarize-ing the image and using the grayscale values as amplitudes. &#xD;
&#xD;
Where to go from here?&#xD;
----------------------&#xD;
&#xD;
We could certainly try to increase the resolution and get everything into a nice little function to do all the steps for us. Another interesting thing would be to add multiple images/slices of a 3 D image into sound, and basically hide an entire 3D object. I&amp;#039;d love to see this being 3D printed.&#xD;
&#xD;
Can you detect the [message in this sound file][14]?&#xD;
&#xD;
Cheers,&#xD;
&#xD;
Marco&#xD;
&#xD;
&#xD;
  [1]: http://www.wolfram.com/language/11/computational-audio/?product=language&#xD;
  [2]: https://www.dropbox.com/s/83788i811rnjn39/secretsound.wav?dl=0&#xD;
  [3]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.21.25.png&amp;amp;userId=48754&#xD;
  [4]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.27.40.png&amp;amp;userId=48754&#xD;
  [5]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.33.34.png&amp;amp;userId=48754&#xD;
  [6]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.39.48.png&amp;amp;userId=48754&#xD;
  [7]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.43.10.png&amp;amp;userId=48754&#xD;
  [8]: http://www.ohmpie.com/imageencode/&#xD;
  [9]: http://www.bbc.co.uk/programmes/b006m9ry&#xD;
  [10]: http://www.evansalazar.com/ohmpie/imageEncode/ohmpie.mp3&#xD;
  [11]: http://www.evansalazar.com/ohmpie/imageEncode/evan.mp3&#xD;
  [12]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.52.56.png&amp;amp;userId=48754&#xD;
  [13]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2016-09-01at00.51.55.png&amp;amp;userId=48754&#xD;
  [14]: https://www.dropbox.com/s/g6cqzute897szrz/finalmessage.wav?dl=0</description>
    <dc:creator>Marco Thiel</dc:creator>
    <dc:date>2016-09-01T00:10:48Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1247481">
    <title>Play Canon with Mathematica</title>
    <link>https://community.wolfram.com/groups/-/m/t/1247481</link>
    <description>I&amp;#039;m a Mathematica novice, so i think there is a lot of space to improve the code. &#xD;
&#xD;
Here is [Youtube Link][1].Hopefully you like it.&#xD;
&#xD;
First I use the Bach&amp;#039;s manuscript as the music score, but the output sound is chaos around the middle part.This score fit to play with the instrument, obviously not Mathematica.&#xD;
![Bach&amp;#039;s manuscript][2]&#xD;
&#xD;
After posting this awful version to my Weibo, my friend told me there is a [Canon played by Matlab][3], it&amp;#039;s so amazing, the most important its score suits for playing with software, so i decided to translate this score from Matlab to Mathematica.&#xD;
&#xD;
## Matlab code ##&#xD;
&#xD;
There are 3 parts in Matlab code.&#xD;
&#xD;
1.First, tell the computer how to make certain sounds.&#xD;
&#xD;
 &#xD;
There is a part of the code in Matlab&#xD;
(I&amp;#039;m a Chinese student, hopefully my poor English didn&amp;#039;t confuse you. I will attach some concepts&amp;#039; wikilink, sorry about that)&#xD;
&#xD;
    % 1/4 notes&#xD;
    do0f = mod4.*cos(2*pi*ScaleTable(21)*f0*t4);&#xD;
    re0f = mod4.*cos(2*pi*ScaleTable(22)*f0*t4);&#xD;
    mi0f = mod4.*cos(2*pi*ScaleTable(23)*f0*t4);&#xD;
    % 1/8 notes&#xD;
    fa0e = mod8.*cos(2*pi*ScaleTable(1)*f0*t8);&#xD;
    so0e = mod8.*cos(2*pi*ScaleTable(2)*f0*t8);&#xD;
    la0e = mod8.*cos(2*pi*ScaleTable(3)*f0*t8);&#xD;
    % 1/16 notes&#xD;
    fa0s = mod16.*cos(2*pi*ScaleTable(1)*f0*t16);&#xD;
    so0s = mod16.*cos(2*pi*ScaleTable(2)*f0*t16);&#xD;
    la0s = mod16.*cos(2*pi*ScaleTable(3)*f0*t16);&#xD;
For clear to see, I just pick few notes information&#xD;
&#xD;
i.$\frac{1}{4}$,$\frac{1}{8}$,$\frac{1}{16}$means [the relative duration of a note][4](https://en.wikipedia.org/wiki/Note_value), the duration of Quarter note is twice that of Eighth note, the duration of 8th note is twice that of 16th note. In the Matlab code, the duration depends on $t4,t8, or\space  t16$&#xD;
&#xD;
 ii.Obviously, &amp;#034;do0f&amp;#034; means the note&amp;#039;s tone. If you plot the  the curve of middle A, it will be like that&#xD;
![Middle A][5]&#xD;
&#xD;
Middle A&amp;#039;s frequency &amp;#034;f&amp;#034; is 440Hz. In the Matlab code, the frequency depends on &amp;#034;$ScaleTable(\space)\times f0$&amp;#034;&#xD;
&#xD;
iii.mod is a modification function, it makes notes sound more soft. the number behind &amp;#034;mod&amp;#034; means it&amp;#039;s duration&#xD;
![mod*Middle A][6]&#xD;
&#xD;
So the Matlab code looks more clear! It becomes$$notename=mod4\times cos(2\pi f t)$$&#xD;
This the way how to make sounds in Matlab.&#xD;
&#xD;
2.Second, tell the computer musical score&#xD;
&#xD;
This part is easy to understand, just input the score.&#xD;
&#xD;
    % Base Melody&#xD;
    cello = [do1f do1f so0f so0f la0f la0f mi0f mi0f... fa0f fa0f do0f do0f fa0f fa0f so0f so0f];......&#xD;
    % Long Melody &#xD;
    violin = [mi2f mi2f re2f re2f do2f do2f ti1f ti1f... la1f la1f so1f so1f la1f la1f ti1f ti1f ......&#xD;
&#xD;
3.Third, arrange the different instruments&amp;#039; sequence&#xD;
&#xD;
Canon is an very interesting music style, you just need to put the same melody at 3 different time points, and done! (I know I didn&amp;#039;t explain it clearly, you can see [Canon&amp;#039;s wiki link][7])&#xD;
&#xD;
It looks beautiful in code&#xD;
&#xD;
    % violin1&#xD;
    v1 = [blkblock violin blkblock blkblock];&#xD;
    % violin2&#xD;
    v2 = [blkblock blkblock violin blkblock];&#xD;
    % violin3&#xD;
    v3 = [blkblock blkblock blkblock violin];&#xD;
     &#xD;
    % Combination&#xD;
    s = c1+v1+v2+v3;&#xD;
    sound(s,fs);&#xD;
&#xD;
## Translate to Mathematica ##&#xD;
&#xD;
We get all information about all notes and musical score, but it&amp;#039;s Matlab code, not Mathematica, we need use Mathematica code translate it.(The Mathematica file at the bottom of the article, it&amp;#039;s a little bit long, so I decided not to paste it here)&#xD;
&#xD;
1. First, make the association between the note name and sound respectively in Mathematica. The output should be like this. I named this association  &amp;#034;nametosoundass&amp;#034;, remember this name.&#xD;
![Note to sound association][8]&#xD;
&#xD;
2.Next, we should get the list of sequence of every instrument should be play.&#xD;
&#xD;
i.Input the raw sequence in Matlab to Mathematica, as you can see, there are many characters we don&amp;#039;t want to get, such as &amp;#034;...&amp;#034;, &amp;#034;%%&amp;#034;, return and whitespace&#xD;
&#xD;
    cellonoteinfo = &#xD;
          &amp;#034;do1f do1f so0f so0f la0f%% la0f mi0f mi0f...fa0f%% fa0f do0f do0f fa0f \n&#xD;
        fa0f so0f so0f&amp;#034;;&#xD;
ii.Define a function to delete these unexpected characters&#xD;
&#xD;
    infotonote[info_] := &#xD;
      StringPartition[StringJoin@StringCases[info, _?LetterQ | _?DigitQ], &#xD;
       4];&#xD;
iii.Get the sequence&#xD;
&#xD;
    In[1]:= cellonote = infotonote[cellonoteinfo]&#xD;
    &#xD;
    Out[1]:= {&amp;#034;do1f&amp;#034;, &amp;#034;do1f&amp;#034;, &amp;#034;so0f&amp;#034;, &amp;#034;so0f&amp;#034;, &amp;#034;la0f&amp;#034;, &amp;#034;la0f&amp;#034;, &amp;#034;mi0f&amp;#034;, &amp;#034;mi0f&amp;#034;, \&#xD;
    &amp;#034;fa0f&amp;#034;, &amp;#034;fa0f&amp;#034;, &amp;#034;do0f&amp;#034;, &amp;#034;do0f&amp;#034;, &amp;#034;fa0f&amp;#034;, &amp;#034;fa0f&amp;#034;, &amp;#034;so0f&amp;#034;, &amp;#034;so0f&amp;#034;}&#xD;
&#xD;
3.Third, replace the note name in sequence by sound, then we will get the sound in sequence. We use the association &amp;#034;notetosoundass&amp;#034;&#xD;
&#xD;
    cello = Sound[Flatten@Table[Replace[cellonote, notetosoundass, 1], 23], {0}];&#xD;
    vio1 = Sound[Replace[violinnote, notetosoundass, 1], {8}];&#xD;
    vio2 = Sound[Replace[violinnote, notetosoundass, 1], {16}];&#xD;
    vio3 = Sound[Replace[violinnote, notetosoundass, 1], {24}];&#xD;
&#xD;
0,8,16,24 at the end of code means the insert time of different instruments.&#xD;
&#xD;
4.Finally, combine it&#xD;
&#xD;
![Completed Canon][9]&#xD;
&#xD;
You can enjoy it [here][10]&#xD;
&#xD;
BTW, this code runs 2 minutes to generate final music, i think it can be better, if you have another idea, glad to see your comment.&#xD;
&#xD;
Both Matlab and Mathematica code are below.&#xD;
&#xD;
&#xD;
  [1]: https://www.youtube.com/watch?v=cVKsSd6Ji1E&amp;amp;t=4s&#xD;
  [2]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Pachelbel%27s_Canon_-_Mus.MS_16481-8_Page_1.jpg&amp;amp;userId=1247466&#xD;
  [3]: https://www.bilibili.com/video/av10699321/?from=search&amp;amp;seid=84894214186229529&#xD;
  [4]: https://en.wikipedia.org/wiki/Note_value&#xD;
  [5]: http://community.wolfram.com//c/portal/getImageAttachment?filename=%E5%B1%8F%E5%B9%95%E5%BF%AB%E7%85%A72017-12-17%E4%B8%8B%E5%8D%886.08.48.png&amp;amp;userId=1247466&#xD;
  [6]: http://community.wolfram.com//c/portal/getImageAttachment?filename=%E5%B1%8F%E5%B9%95%E5%BF%AB%E7%85%A72017-12-17%E4%B8%8B%E5%8D%886.16.13.png&amp;amp;userId=1247466&#xD;
  [7]: https://en.wikipedia.org/wiki/Canon_%28music%29&#xD;
  [8]: http://community.wolfram.com//c/portal/getImageAttachment?filename=%E5%B1%8F%E5%B9%95%E5%BF%AB%E7%85%A72017-12-17%E4%B8%8B%E5%8D%886.54.08.png&amp;amp;userId=1247466&#xD;
  [9]: http://community.wolfram.com//c/portal/getImageAttachment?filename=%E5%B1%8F%E5%B9%95%E5%BF%AB%E7%85%A72017-12-17%E4%B8%8B%E5%8D%887.31.58.png&amp;amp;userId=1247466&#xD;
  [10]: https://www.youtube.com/watch?v=cVKsSd6Ji1E&amp;amp;t=4s</description>
    <dc:creator>QiuHao Chen</dc:creator>
    <dc:date>2017-12-17T07:15:02Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2328597">
    <title>Training a recurrent neural network (RNN) to generate piano music</title>
    <link>https://community.wolfram.com/groups/-/m/t/2328597</link>
    <description>&amp;gt; **GitHub Repository:** https://github.com/alecGraves/Howl&#xD;
&#xD;
&#xD;
&#xD;
&amp;amp;[Wolfram Notebook][1]&#xD;
&#xD;
&#xD;
  [1]: https://www.wolframcloud.com/obj/da6d3b76-7bbf-4a55-9fcd-058e7f1e17bf</description>
    <dc:creator>Alec Graves</dc:creator>
    <dc:date>2021-07-27T14:09:12Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2228704">
    <title>Computational Parenting: Are we nearly there yet?</title>
    <link>https://community.wolfram.com/groups/-/m/t/2228704</link>
    <description>Introduction&#xD;
------------------&#xD;
&#xD;
This is a light-hearted little piece of code I wrote to help deal with questions like &amp;#034;Are we nearly there yet?&amp;#034; of young children when driving a car. &#xD;
&#xD;
Here is the idea. My daughter is in second class and has learnt to count, but it takes time for children  to appreciate numbers and magnitudes. This is an important part of &amp;#034;[Computational Thinking][1]&amp;#034;; there is a sort of progression when children learn how to count and work with numbers. Based on my observation (and that is based on a sample of 2 or so), counting starts with very concrete objects like pieces of chocolate or building bricks or so. Only later will children learn to appreciate numbers as more abstract entities. It is typical that little children struggle to understand the magnitude of a number - they might be quite poor at estimating ages of people for a long time and putting numbers in perspective. (&amp;#034;How come that 1000$ is a lot, but 1000 grains of sand is too little to play with?&amp;#034;)&#xD;
&#xD;
If I answer the question &amp;#034;Are we nearly there yet?&amp;#034; with &amp;#034;30 minutes from now.&amp;#034; It doesn&amp;#039;t necessarily mean much. Saying &amp;#034;one episode of your favourite program&amp;#034; appears to be a more meaningful answer.&#xD;
&#xD;
Now, we came up with this concept, where I basically tell my daughter to count to a certain number: &#xD;
Clara: &amp;#034;How long until my food is ready?&amp;#034;&#xD;
Me:&amp;#034;Count to 150.&amp;#034;&#xD;
&#xD;
Now I could do this very simply. There are all these calculations like: &amp;#034;To what number could I count if I were counting at a rate of one number per second and were to count all my life?&amp;#034;&#xD;
&#xD;
![enter image description here][2] &#xD;
&#xD;
gives 72.6yr, which I can then UnitConvert to seconds:&#xD;
&#xD;
    UnitConvert[Quantity[72.6, &amp;#034;Years&amp;#034;], &amp;#034;Seconds&amp;#034;]&#xD;
&#xD;
That gives about 2.29 * 10^ 9 seconds and that would be what a person could count to if they start counting when they are born, and never sleep or do anything else, and get to say one number per second. Some of these assumptions might not be realistic.&#xD;
&#xD;
Coding actual counting&#xD;
-------------------------------&#xD;
&#xD;
I was interested in the actual counting time, i.e. ignoring sleep, breaks etc, and just wondering how many numbers I could really say in a given time, if I didn&amp;#039;t do anything else. So I could ask Mathematica to make a sound file and speaking numbers for me. Counting up to 10 (at a reasonable speed) would look like this:&#xD;
&#xD;
    SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ Range[10], &#xD;
    &amp;#034;,  &amp;#034;]]&#xD;
&#xD;
Using Duration, I can find out how long it takes to say this:&#xD;
&#xD;
    Duration[SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ Range[10], &amp;#034;,  &amp;#034;]]]&#xD;
&#xD;
I obtain 6.45732 s, which is too high a precision for my taste, but gives me an idea of how long it takes to count up to 10. So it takes an average of 0.645732 seconds to say one of the numbers. As numbers become larger, it will take longer to say them. Let&amp;#039;s count up to 100:&#xD;
&#xD;
    Duration[SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ Range[100], &amp;#034;,  &amp;#034;]]]&#xD;
&#xD;
which gives me 1min 44.4055 seconds, which is about 1.046 seconds per number. Counting up to 1000 is still an easy thing to do:&#xD;
&#xD;
    Duration[SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ Range[1000],&amp;#034;,  &amp;#034;]]]&#xD;
&#xD;
gives 27 min 50.0569 seconds, which is on average 1.67007 seconds per number. Now I could produce longer and longer sound files, but if I count up to larger numbers that is not the most practical thing to do. So lets do a random sampling approach. If we want to estimate how long it takes to count to one million, I could ask Mathematica to choose 100 numbers and then scale up to 1.000.000:&#xD;
&#xD;
    1000000/100*Duration[SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ RandomSample[Range[1000000], 100], &amp;#034;,  &amp;#034;]]]&#xD;
&#xD;
Every time you run this you get slightly different results. Here are the results from 10 &amp;#034;realisations&amp;#034;:&#xD;
&#xD;
![enter image description here][3]&#xD;
&#xD;
Of course, I can get better estimates by sampling more than 100 numbers. I would also like to use mixed units so give a better idea of the times. Here is a simple piece of code to do this:&#xD;
&#xD;
    Monitor[&#xD;
    results = Table[{k, UnitConvert[k/1000*Duration[SpeechSynthesize[&#xD;
            StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ &#xD;
              RandomSample[Range[k], 1000], &amp;#034;,  &amp;#034;]]], &#xD;
         MixedUnit[{&amp;#034;Years&amp;#034;, &amp;#034;Months&amp;#034;, &amp;#034;Days&amp;#034;, &amp;#034;Hours&amp;#034;, &amp;#034;Minutes&amp;#034;, &#xD;
           &amp;#034;Seconds&amp;#034;}]]}, {k, NestList[10*# &amp;amp;, 1000, 6]}], k]&#xD;
&#xD;
Not the most elegant piece of code, but it gets the job done:&#xD;
&#xD;
![enter image description here][4]&#xD;
&#xD;
Other languages&#xD;
-----------------------&#xD;
Of course, we can try this in different languages:&#xD;
&#xD;
    Monitor[resultsgerman = &#xD;
      Table[{k, UnitConvert[k/1000*Duration[SpeechSynthesize[&#xD;
            StringRiffle[IntegerName[#, Language -&amp;gt; &amp;#034;German&amp;#034;] &amp;amp; /@ &#xD;
              RandomSample[Range[k], 1000], &amp;#034;, &amp;#034;], Language -&amp;gt; &amp;#034;German&amp;#034;]],&#xD;
          MixedUnit[{&amp;#034;Years&amp;#034;, &amp;#034;Months&amp;#034;, &amp;#034;Days&amp;#034;, &amp;#034;Hours&amp;#034;, &amp;#034;Minutes&amp;#034;, &#xD;
           &amp;#034;Seconds&amp;#034;}]]}, {k, NestList[10*# &amp;amp;, 1000, 6]}], k]&#xD;
&#xD;
which gives:&#xD;
&#xD;
![enter image description here][5]&#xD;
&#xD;
So it appears that Germans count a bit more slowly than English native speakers. Let&amp;#039;s have a look at Spanish:&#xD;
&#xD;
    Monitor[resultsspanish = &#xD;
      Table[{k, UnitConvert[k/1000*Duration[SpeechSynthesize[&#xD;
            StringRiffle[IntegerName[#, Language -&amp;gt; &amp;#034;Spanish&amp;#034;] &amp;amp; /@ &#xD;
            RandomSample[Range[k], 1000], &amp;#034;, &amp;#034;], Language -&amp;gt; &amp;#034;Spanish&amp;#034;]], &#xD;
         MixedUnit[{&amp;#034;Years&amp;#034;, &amp;#034;Months&amp;#034;, &amp;#034;Days&amp;#034;, &amp;#034;Hours&amp;#034;, &amp;#034;Minutes&amp;#034;, &#xD;
           &amp;#034;Seconds&amp;#034;}]]}, {k, NestList[10*# &amp;amp;, 1000, 6]}], k]&#xD;
&#xD;
which gives:&#xD;
&#xD;
![enter image description here][6]&#xD;
&#xD;
I tried some other languages, too, but that doesn&amp;#039;t contribute a lot to this parenting problem. &#xD;
&#xD;
Higher resolution&#xD;
----------------------&#xD;
&#xD;
For the next application, I want some higher resolution data for English.&#xD;
&#xD;
    Monitor[resultsEnglishHighRes = &#xD;
      Table[{k, UnitConvert[k/Min[1000, k]*&#xD;
      Duration[SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ &#xD;
      RandomSample[Range[k], Min[1000, k]], &amp;#034;,  &amp;#034;]]], &#xD;
         MixedUnit[{&amp;#034;Years&amp;#034;, &amp;#034;Months&amp;#034;, &amp;#034;Days&amp;#034;, &amp;#034;Hours&amp;#034;, &amp;#034;Minutes&amp;#034;, &#xD;
           &amp;#034;Seconds&amp;#034;}]]}, {k, Floor /@ Table[10^k, {k, 1, 9, 1/10}]}], k]&#xD;
&#xD;
This gives me a long table; I&amp;#039;ll only show every second entry though:&#xD;
&#xD;
![enter image description here][7]&#xD;
&#xD;
That&amp;#039;s some serious counting going on right here....&#xD;
If we plot this, we get:&#xD;
&#xD;
    ListLogLogPlot[{#[[1]], QuantityMagnitude[UnitConvert[#[[2]], &amp;#034;Seconds&amp;#034;]]} &amp;amp; /@ &#xD;
    resultsEnglishHighRes, PlotRange -&amp;gt; All, LabelStyle -&amp;gt; Directive[Bold, Medium], &#xD;
    AxesLabel -&amp;gt; {&amp;#034;Count to&amp;#034;, &amp;#034;Time in seconds&amp;#034;}, PlotStyle -&amp;gt; Red]&#xD;
&#xD;
![enter image description here][8]&#xD;
&#xD;
We can also calculate the average time per number if we count up:&#xD;
&#xD;
    averagetime={#[[1]], QuantityMagnitude[UnitConvert[#[[2]], &amp;#034;Seconds&amp;#034;]]/#[[&#xD;
         1]]} &amp;amp; /@ resultsEnglishHighRes;&#xD;
    &#xD;
    ListLogLogPlot[averagetime, LabelStyle -&amp;gt; Directive[Bold, Medium], &#xD;
     AxesLabel -&amp;gt; {&amp;#034;Count up to&amp;#034;, &amp;#034;&amp;lt;time&amp;gt; per number in secs&amp;#034;}]&#xD;
&#xD;
![enter image description here][9]&#xD;
&#xD;
Making this into parenting approved functions&#xD;
---------------------------------------------------------&#xD;
&#xD;
Of course, these graphs tell me how long it takes to count up to a certain number, but they do not allow me to answer my daughter&amp;#039;s questions.... So I need to build something to make predictions about how far she has to count until we arrive. We could do some simple curve fitting, but if we are too lazy (and I sure am), we can use Mathematica&amp;#039;s more advanced features to get this done - quick and dirty.&#xD;
&#xD;
Let&amp;#039;s try two things:&#xD;
&#xD;
(i) Let&amp;#039;s predict how long we need to count to a certain number.&#xD;
(ii) Predict the number we have to count to if we need to count for a given time.&#xD;
&#xD;
Let&amp;#039;s predict how long we need to count to a certain number&#xD;
-----------------------------------------&#xD;
&#xD;
Easy peasy. Here&amp;#039;s a predictor &#xD;
&#xD;
    ptime = Predict[&#xD;
      Rule @@@ ({#[[1]], UnitConvert[#[[2]], &amp;#034;Seconds&amp;#034;]} &amp;amp; /@ &#xD;
         resultsEnglishHighRes), PerformanceGoal -&amp;gt; &amp;#034;Quality&amp;#034;]&#xD;
&#xD;
It&amp;#039;s ok, but it doesn&amp;#039;t give us units so let&amp;#039;s do this:&#xD;
&#xD;
    UnitConvert[ptime[1000000], &#xD;
     MixedUnit[{&amp;#034;Years&amp;#034;, &amp;#034;Months&amp;#034;, &amp;#034;Days&amp;#034;, &amp;#034;Hours&amp;#034;, &amp;#034;Minutes&amp;#034;, &#xD;
       &amp;#034;Seconds&amp;#034;}]]&#xD;
&#xD;
So this predicts how long I have to count up to a million. I get:&#xD;
&#xD;
1 mo 11 days 18h 21 min 26.8809s&#xD;
&#xD;
As before, this won&amp;#039;t be as precise as it pretends to be (!) and also is a wee bit different from my direct (but sampled) counting approach, which gave me:&#xD;
&#xD;
1 mo 6 days 15h 32 min 21.4512 s&#xD;
&#xD;
But then it is hopefully going to be more precise than the &amp;#034;one-number-per-second&amp;#034; assumption.&#xD;
&#xD;
Predict the number we have to count to if we need to count for a given time&#xD;
--------------------&#xD;
&#xD;
Luckily there is not much brain-CPU-time required for this either. &#xD;
&#xD;
    preversetime = Predict[Rule @@@ ({QuantityMagnitude[UnitConvert[#[[2]], &amp;#034;Seconds&amp;#034;]], #[[1]]} &amp;amp; /@ &#xD;
    resultsEnglishHighRes), PerformanceGoal -&amp;gt; &amp;#034;Quality&amp;#034;]&#xD;
&#xD;
We can then add units and use units etc as above.&#xD;
&#xD;
Application&#xD;
-------------&#xD;
&#xD;
Ok, now here&amp;#039;s an ***hypothetical*** application - or an experiment which is of course not currently possible due to COVID restrictions.&#xD;
&#xD;
[planning to drive from Aberdeen to Edinburgh in Scotland]&#xD;
&#xD;
Clara: &amp;#034;Are we nearly there yet?&amp;#034;&#xD;
Me: &amp;#034;No, we are still in front of our house.&amp;#034;&#xD;
Clara: &amp;#034;What do I have to count to?&amp;#034;&#xD;
Me: [takes out phone, opens Wolfram Cloud website (see below)] : &amp;#034;Count to 3573.&amp;#034;&#xD;
&#xD;
Crisis averted. Happy child, happy parent.&#xD;
&#xD;
Here&amp;#039;s how it works:&#xD;
&#xD;
    Ceiling[preversetime[UnitConvert[TravelTime[Entity[&amp;#034;City&amp;#034;, {&amp;#034;Aberdeen&amp;#034;, &amp;#034;AberdeenCity&amp;#034;, &amp;#034;UnitedKingdom&amp;#034;}], Entity[&amp;#034;City&amp;#034;, {&amp;#034;Edinburgh&amp;#034;, &amp;#034;Edinburgh&amp;#034;, &amp;#034;UnitedKingdom&amp;#034;}]], &amp;#034;Seconds&amp;#034;]]]&#xD;
&#xD;
Then you deploy that to the Cloud:&#xD;
&#xD;
    CloudDeploy[FormFunction[{&amp;#034;from&amp;#034; -&amp;gt; &amp;#034;Location&amp;#034;, &amp;#034;to&amp;#034; -&amp;gt; &amp;#034;Location&amp;#034;}, &#xD;
    Ceiling[preversetime[UnitConvert[TravelTime[#from, #to], &amp;#034;Seconds&amp;#034;]]] &amp;amp;], Permissions -&amp;gt; &amp;#034;Public&amp;#034;]&#xD;
&#xD;
and get a link to a website. Good times!&#xD;
&#xD;
Conclusion&#xD;
--------------&#xD;
&#xD;
There are lots of things that can be improved and should be checked. All numbers were computed using a random subsample approach. So we would need to know error bars etc. That can be done, but is out of the scope of this post. We can run some easy tests though. For example:&#xD;
&#xD;
    TravelTime[&#xD;
     Entity[&amp;#034;City&amp;#034;, {&amp;#034;Aberdeen&amp;#034;, &amp;#034;AberdeenCity&amp;#034;, &amp;#034;UnitedKingdom&amp;#034;}], &#xD;
     Entity[&amp;#034;City&amp;#034;, {&amp;#034;Edinburgh&amp;#034;, &amp;#034;Edinburgh&amp;#034;, &amp;#034;UnitedKingdom&amp;#034;}]]&#xD;
&#xD;
Gives 2 h 11 mins. The predictor suggests that I should count to 3573. Well, let&amp;#039;s quickly do that and see how long it takes:&#xD;
&#xD;
    UnitConvert[Duration[SpeechSynthesize[StringRiffle[StringReplace[IntegerName[#], &amp;#034;\[Hyphen]&amp;#034; -&amp;gt; &amp;#034; &amp;#034;] &amp;amp; /@ Range[3573], &amp;#034;,  &amp;#034;]]],MixedUnit[{ &amp;#034;Hours&amp;#034;, &amp;#034;Minutes&amp;#034;, &amp;#034;Seconds&amp;#034;}]]&#xD;
&#xD;
That gives 2 h 6 mins 24.2026s (with overwhelming precision!). Not too bad. The code has not been properly beta-tested and there might be bugs. I have not tried to count up to 1000000000 or so to check the results; this is basically due to my very limited life span. Also, I did not even try to make the code nice or efficient. It was basically just typing it in and getting it done - so there are lots of improvements to be made there.&#xD;
&#xD;
Of course, the cloud version can be adjusted to estimate the number to count to for any given period of time so that it becomes more useful for everyday parenting.&#xD;
&#xD;
All the best from Scotland,&#xD;
Marco&#xD;
&#xD;
&#xD;
&#xD;
  [1]: https://www.computerbasedmath.org&#xD;
  [2]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Averagelife.png&amp;amp;userId=48754&#xD;
  [3]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at13.57.20.png&amp;amp;userId=48754&#xD;
  [4]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at14.00.54.png&amp;amp;userId=48754&#xD;
  [5]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at14.05.50.png&amp;amp;userId=48754&#xD;
  [6]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at14.19.14.png&amp;amp;userId=48754&#xD;
  [7]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at14.29.32.png&amp;amp;userId=48754&#xD;
  [8]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at14.32.56.png&amp;amp;userId=48754&#xD;
  [9]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Screenshot2021-03-25at14.35.46.png&amp;amp;userId=48754&#xD;
  [10]: https://www.wolframcloud.com/obj/3c7431be-0c82-477f-8ede-f3ba1eb8d0c4</description>
    <dc:creator>Marco Thiel</dc:creator>
    <dc:date>2021-03-25T15:11:00Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/2386951">
    <title>The sound of minute repeater: computational analysis &amp;amp; synthesis</title>
    <link>https://community.wolfram.com/groups/-/m/t/2386951</link>
    <description>&amp;amp;[Wolfram Notebook][1]&#xD;
&#xD;
&#xD;
&#xD;
  [1]: https://www.wolframcloud.com/obj/a5b26a59-e94c-4335-a06d-be68868e3a88&#xD;
&#xD;
&#xD;
&#xD;
&#xD;
&#xD;
  [Original NB]: https://www.wolframcloud.com/obj/169c961e-e735-4ced-bafe-8b2f7440e60a</description>
    <dc:creator>James Lu</dc:creator>
    <dc:date>2021-10-18T02:02:33Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/1383630">
    <title>[WSC18] Analyzing and visualizing chord sequences in music</title>
    <link>https://community.wolfram.com/groups/-/m/t/1383630</link>
    <description>During this year&amp;#039;s Wolfram Summer Camp, being mentored by Christian Pasquel, I developed a tool that identifies chord sequences in music (from MIDI files) and generates a corresponding graph. The graph represents all [unique] chords as vertices, and connects every pair of chronologically subsequent chords with a directed edge. Here is an example of a graph I generated:&#xD;
&#xD;
![Graph genehrated from Bach&amp;#039;s prelude no.1 of the Well Tempered Klavier (Book I)][1]&#xD;
&#xD;
&#xD;
Below is a detailed account on the development and current state of the project, plus some background on the corresponding musical theory notions.&#xD;
&#xD;
#Introduction&#xD;
&#xD;
&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;**GOAL** | The aim of this project is to develop a utility that identifies chords (e.g. C Major, A minor, G7, etc.) from MIDI files, in chronological order, and then generates a graph for visualizing that chord sequence. In the graph, each vertex would represent a unique chord, and each pair chronologically adjacent chords would be connected by a directed edge (i.e. an arrow). So, for example, if at some point in the music that is being analyzed there is a transition from a major G chord to a major C chord, there would be an arrow that goes from the G Major chord to the C Major chord. Therefore, the graph would describe a [Markov chain][2] for the chords. The purpose of the graph is to visualize frequent chord sequences and progressions within a certain piece of music.&#xD;
&#xD;
&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;&amp;amp;nbsp;**MOTIVATION** | While brainstorming for project ideas, I don&amp;#039;t know why, I had a desire to do something with graphs. Then I asked myself, &amp;#034;What are graphs good at modelling?&amp;#034;. I mentally browsed through my areas of interest, searching for any that matched that requirement. One of my main interests is music; I am somewhat of a musician myself. And, in fact, [musical] harmony *is* a good subject to be modelled by graphs. Harmony, one of the fundamental pillars of music (and perhaps the most important), not only involves the chords themselves, but, more significantly, the *transitions* between those, which is what gives character to music. And directed graphs, and, specifically, Markov models, are a perfect match for transitions between states.&#xD;
&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
#Some background&#xD;
*Skip this if you aren&amp;#039;t interested in the musical theory part or if you already have a background in music theory!*&#xD;
&#xD;
##What is a chord?&#xD;
A chord is basically a group of notes played together (contemporarily). Chords are the quanta of musical &amp;#034;feeling&amp;#034;; the typicalbut somewhat naïveexample is the sensation of major chords sounding &amp;#034;happy&amp;#034; and minor chords sounding &amp;#034;sad&amp;#034; or melancholic (more on types of chords later). &#xD;
&#xD;
Types of chords are defined by the [intervals][3] (distance in pitch) between the notes. The *root* of a chord is the &amp;#034;most important&amp;#034; or fundamental note of the cord, in the sense that it is the &amp;#034;base&amp;#034; from which the aforementioned intervals are measured. In other words, the archetype of chord defines the &amp;#034;feel&amp;#034; and the general harmonic properties of the chord, while the root defines the pitch of the chord. So a &amp;#034;C Major&amp;#034; chord is a chord with archetype &amp;#034;major triad&amp;#034; (more on that later) built on the note C; i.e., its root is C.&#xD;
&#xD;
The *sequence* of chords in a piece constitutes its **harmony**, and it can convey much more complex musical messages or feelings than a single chord, just as in language: a single word does have meaning, but a sentence can have a much more complex meaning than any single word.&#xD;
&#xD;
##Patterns in chord sequences&#xD;
The main difference that between language and music is that language, in general, has a much stricter structure (i.e. the order of words, a.k.a. syntax) than music: the latter is an art, and there are no predetermined rules to follow. But humans \[have a tendency to\] like patterns, and music wouldn&amp;#039;t be so universally beloved if it didn&amp;#039;t contain any patterns. This also explains the unpopularity of [atonal music][4] (example [here][5]). But even atonal music has patterns: it may do its best to avoid harmonic patterns, but it still contains some level of rythmic, textural or other kinds of patterns.&#xD;
&#xD;
This is why using graphs to visualize chord sequences is interesting: it is a semidirect way of identifying the harmonic patterns that distinguish different genres, styles, forms, pieces or even fragments of music. In my project, I have mainly focused on the &amp;#034;western&amp;#034; conception of tonal music, an particularly in its &amp;#034;classical&amp;#034; version (what I mean by &amp;#034;classical&amp;#034; is, in lack of a better definition, a classification that encompasses all music where the composer is, culturally, the most important artist). That doesn&amp;#039;t mean this tool isn&amp;#039;t apt for other types of music; it just means it will analyze it from this specific standpoint.&#xD;
&#xD;
In tonal music, the harmonic patterns are all related to a certain notion of &amp;#034;center of gravity&amp;#034;: the [*tonic*][6], which is, in some way the music&amp;#039;s harmonic &amp;#034;home&amp;#034;. Classical (as in pre-XX-century) tonal music usually ends (and often starts) with the tonic chord. In fact, we can further extend the analogy with gravity by saying that music consists in a game of tension, in which the closer you are to the center of gravity (the tonic), the greater the &amp;#034;pull&amp;#034;. In an oversimplified manner, the musical equivalent of the [Schwarzschild radius][7]  is the [dominant chord][8]: it tends towards the tonic. Well, not really, because you *can* turn back from itand in fact a lot of interesting harmonical sequences consist in doing just that.&#xD;
&#xD;
##Some types of chords&#xD;
In &amp;#034;classical&amp;#034; music (see definition above), there are mainly these kinds of chords (based on the amount of unique notes they contain): triad chords (i.e. three-note chords), seventh chords (i.e. four-note chords; we&amp;#039;ll see why they&amp;#039;re called *seventh* in a bit), and ninth chords (five-note chords). There is another main distinction: major and minor chords (i.e. the cliché &amp;#034;happy&amp;#034; vs &amp;#034;sad&amp;#034; distinction). &#xD;
&#xD;
###Triad chords&#xD;
Probably the most simple and frequent chord is the triad chord (either major or minor). Here is a picture of a major and a minor triad C chord (left to right):&#xD;
&#xD;
![Major and minor triad C chords (ltr)][9]&#xD;
&#xD;
###Seventh chords&#xD;
[Seventh chords][10] are called so because they contain a seventh [interval][11]. Their main significance is in dominant chords, where they usually appear in the major-triad-minor-seventh (a.k.a [&amp;#034;dominant&amp;#034;][12]) form. Another important seventh chord form is the fully diminished seventh chord (these will be relevant for the code later), which also tends to resolve (&amp;#034;resolve&amp;#034; is music jargon for &amp;#034;transition to a chord with less tension&amp;#034;) to tonic.&#xD;
&#xD;
![Seventh chords][13]&#xD;
&#xD;
###Ninth chords&#xD;
Although not extremely frequent, they do appear in classical music. The most &amp;#034;popular&amp;#034; is the dominant ninth chord (an extension of the dominant 7th). An alternative for this chord is the minor ninth dominant chord (built from the same dominant 7th chord, but with a minor ninth instead).&#xD;
&#xD;
&amp;lt;br&amp;gt;&#xD;
&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
#Algorithms and Code&#xD;
In this section I&amp;#039;m going to walk through my code in order of execution. Four main parts can be distinguished in my project: importing and preprocessing, splitting the note sequence into &amp;#034;chunks&amp;#034; to be analyzed as chords, identifying the chord in each of those chunks, and visualizing the whole sequence as a graph.&#xD;
&#xD;
##First phase: importing and preprocessing the MIDI file&#xD;
The first operation that needs to be done is importing the MIDI file and preprocessing it. This includes selecting which elements to import from the file, converting them to a given simplified form, and performing any sorting, deletion of superfluous elements, or other modification that needs to be done.&#xD;
&#xD;
For this purpose I defined the function `importMIDI`:&#xD;
	&#xD;
	importMIDI[filename_String] := MapAt[Flatten[#, 1] &amp;amp;, MapAt[flattenAndSortSoundNotes, &#xD;
           Import[(dir &amp;lt;&amp;gt; filename &amp;lt;&amp;gt; &amp;#034;.mid&amp;#034;), {{&amp;#034;SoundNotes&amp;#034;, &amp;#034;Metadata&amp;#034;}}], &#xD;
	1], 2]&#xD;
&#xD;
Here `dir` stands for the directory where I saved all my MIDIs (to avoid having to type in the whole directory every time). Notice that we&amp;#039;re importing the music as SoundNotes *and* the file&amp;#039;s metadatawe will need it for determining the boundaries of measures (see below). The function `flattenAndSortNotes` does what it sound like: it converts the list of `SoundNote`s that `Import` returned into a flattened list of notes (i.e. a single track), sorted by their starting time. It also gets rid of anything that isn&amp;#039;t necessary for chord identification (i.e. rhythmic sounds or effects). Consult the attached notebook for the explicit definition.&#xD;
&#xD;
Here is the format the sequence of notes is returned in (i.e. `importMIDI[...][[1]]`):&#xD;
&#xD;
    {{&amp;#034;C4&amp;#034;, {0., 1.4625}}, {&amp;#034;E4&amp;#034;, {0.18125, 1.4625}}, {&amp;#034;G4&amp;#034;, {0.36875, 0.525}}, &amp;lt;&amp;lt;562&amp;gt;&amp;gt;, {&amp;#034;G2&amp;#034;, {105., 107.963}}, {&amp;#034;G4&amp;#034;, {105., 107.963}}}&#xD;
&#xD;
Each sub-list represents a note. Its first element is the actual pitch; the second is a list that represents the timespan (i.e. start and end time in seconds).&#xD;
&#xD;
&amp;lt;br&amp;gt;&#xD;
&#xD;
##Second phase: splitting the note sequence into chunks&#xD;
The challenge in this part of the project is knowing how to determine which notes form a single chord; i.e., where to put the boundary between one chord and the next. &#xD;
&#xD;
The solution I came up with is not optimal, but, until now, nothing better has occurred to me (suggestions are welcome!). It involves determining where each measure start/end lies in time from the metadata and splitting each of those into a certain amount of sub-parts; then the notes are grouped by the specific sub-part of the specific measure they pertain to.  The rationale behind this is that chords in classical music tend to be well-contained within measures or rational fractions of these.&#xD;
&#xD;
This procedure is contained in the function `chordSequenceAnalyzeUsingMeasures`. I&amp;#039;m going to go over it quickly:&#xD;
&#xD;
    chordSequenceUsingMeasures[midiData_List /; Length@midiData == 2, &#xD;
      measureSplit_: 2, analyzer_String: &amp;#034;Heuristic&amp;#034;] := &#xD;
     Block[{noteSequence, metadata,  chunkKeyframes, chunkedSequence, &#xD;
       result},&#xD;
      &#xD;
&#xD;
      (*Separate notes from metadata*)&#xD;
      noteSequence = midiData[[1]];&#xD;
      metadata = midiData[[2]];&#xD;
      &#xD;
Until here it&amp;#039;s pretty self evident.&#xD;
&#xD;
      (*Get measure keyframes*)&#xD;
      chunkKeyframes = &#xD;
       divideByN[&#xD;
        measureKeyframesFromMetadata[&#xD;
         metadata, (Last@noteSequence)[[2, 2]]], measureSplit]; &#xD;
&#xD;
Here the function `measureKeyframesFromMetadata` is called. It fetches all of the `TimeSignature` and `SetTempo` tags in the metadata and identifies the position of each measure from them. `divideByN` subdivides each measure by `measureSplit` (an optional argument with default value `2`).&#xD;
      &#xD;
      (*Chunk sequence*)&#xD;
      chunkedSequence = {};&#xD;
      Module[{i = 1},&#xD;
       Do[&#xD;
        With[{k0 = chunkKeyframes[[j]], k1 = chunkKeyframes[[j + 1]]}, &#xD;
         Module[{chunk = {}}, &#xD;
          While[&#xD;
           i &amp;lt;= Length@noteSequence &amp;amp;&amp;amp; ( &#xD;
             k0 &amp;lt;= noteSequence[[i, 2, 1]] &amp;lt; k1 || &#xD;
              k0 &amp;lt; noteSequence[[i, 2, 2]] &amp;lt;= k1 ), &#xD;
           AppendTo[chunk, noteSequence[[i]]] i++;]; &#xD;
          AppendTo[chunkedSequence, chunk]&#xD;
          ]&#xD;
         ], &#xD;
        {j, Length@chunkKeyframes - 1}]];&#xD;
      chunkedSequence = &#xD;
       DeleteCases[chunkedSequence, l_List /; Length@l == 0];&#xD;
&#xD;
Once the measures&amp;#039; timespan has been determined, a list of &amp;#034;chunks&amp;#034; (lists of notes grouped by measure part) is generated. &#xD;
      &#xD;
      (*Call analyzer*)&#xD;
      Switch[analyzer,&#xD;
       &amp;#034;Deterministic&amp;#034;, result = chordChunkAnalyze /@ chunkedSequence,&#xD;
       &amp;#034;Heuristic&amp;#034;, &#xD;
       result = heuristicChordAnalyze /@ justPitch /@ chunkedSequence&#xD;
       ];&#xD;
      &#xD;
      result = resolveDiminished7th[Split[result][[All, 1]]]&#xD;
      ]&#xD;
&#xD;
Finally, each chunk is  sent to the chord analyzer function `heuristicChordAnalyze`, which I&amp;#039;ll talk about in the next section, along with the currently mysterious `resolveDiminished7th`. &#xD;
&#xD;
Since this algorithm for &amp;#034;chunking&amp;#034; a note sequence doesn&amp;#039;t work for everything, I also developed an alternative, more naïve approach:&#xD;
&#xD;
    chordSequenceNaïve[midiData_List /; Length@midiData == 2, &#xD;
      analyzer_String: &amp;#034;Heuristic&amp;#034;, n1_Integer: 6, n2_Integer: 1] := &#xD;
     Module[{noteSequence, chunkedSequence, result},&#xD;
      &#xD;
      (*Separate notes from metadata*)&#xD;
      noteSequence = midiData[[1]];&#xD;
      &#xD;
      (*Chunk sequence*)&#xD;
      chunkedSequence = Partition[noteSequence, n1, n2];&#xD;
      &#xD;
      (*Call analyzer*)&#xD;
      result = heuristicChordAnalyze /@ justPitch@chunkedSequence;&#xD;
      &#xD;
      result = resolveDiminished7th[Split[result][[All, 1]]]&#xD;
      ]&#xD;
&#xD;
&amp;lt;br&amp;gt;&#xD;
&#xD;
##Phase 3: identifying the chord from a group of notes&#xD;
&#xD;
This has been the main conceptual challenge in the whole project. After some unsucsessful ideas, with some suggestions from Rob Morris (one of the mentors), whom I thank, I ended up developing the following algorithm. It iterates through each note and assigns it a score that represents the likeliness of that note being the root of the chord based on the presence of certain indicators (i.e. notes the presence of which define a chord, to some degree), each of which with a different weight: having a fifth, having a third, a minor seventh... Then the note with the highest chord is assumed to be the root of the chord.&#xD;
&#xD;
In code:&#xD;
&#xD;
	heuristicChordAnalyze[notes_List] := &#xD;
	 Block[{chordNotes, scores, root},&#xD;
	  &#xD;
	  (*Calls to helper functions*)&#xD;
	  chordNotes = octaveReduce /@ convertToSemitones /@ notes // DeleteDuplicates;&#xD;
	  &#xD;
	  (*Scoring*)&#xD;
	  scores = Table[Total@&#xD;
      Pick[&#xD;
       (*Score points*)&#xD;
       {24, 16, 16, 8, 2, 3, 1, 1,&#xD;
        10, 15, 15, 18},&#xD;
       &#xD;
       (*Conditions*)&#xD;
       SubsetQ[chordNotes, #] &amp;amp; /@octaveReduce /@&#xD;
          {{nt + 7}, {nt + 4}, {nt + 3}, {nt + 10}, {nt + 11}, {nt + 2}, {nt + 5}, {nt + 9},&#xD;
          {nt + 4, nt + 10}, {nt + 3, nt + 6, nt + 10}, {nt + 3, nt + 6, nt + 9}, {nt + 1, nt + 4, nt + 10}}&#xD;
       ]&#xD;
     &#xD;
         (*Substract outliers*)&#xD;
         - 18*Length@Complement[chordNotes, octaveReduce /@ {nt, 7 + nt, 4 + nt, 3 + nt, 10 + nt, 11 + nt, &#xD;
                                                             2 + nt, 5 + nt, 9 + nt, 6 + nt}],&#xD;
    	&#xD;
       {nt, chordNotes}];&#xD;
&#xD;
	  (*Return*)&#xD;
	  root = Part[chordNotes, Position[scores, Max @@ scores][[1, 1]]];&#xD;
	  &#xD;
	  {root, Which[&#xD;
        SubsetQ[chordNotes, octaveReduce /@ {root + 10 , root + 2, root + 5, root + 9}], &amp;#034;13&amp;#034;,&#xD;
        SubsetQ[chordNotes, octaveReduce /@ {root + 10, root + 2, root + 5}], &amp;#034;11&amp;#034;,&#xD;
        SubsetQ[chordNotes, octaveReduce /@ {root + 4, root + 10, root + 2}], &amp;#034;Dom9&amp;#034;,&#xD;
        SubsetQ[chordNotes, octaveReduce /@ {root + 4, root + 10, root + 1}], &amp;#034;Dom9m&amp;#034;,&#xD;
        SubsetQ[chordNotes, octaveReduce /@ {root + 11, root + 7, root + 3}], &amp;#034;m7M&amp;#034;,&#xD;
        SubsetQ[chordNotes, {octaveReduce[root + 11], octaveReduce[root + 4]}],  &amp;#034;7M&amp;#034;,&#xD;
        SubsetQ[chordNotes, {octaveReduce[root + 10], octaveReduce[root + 4]}],  &amp;#034;Dom7&amp;#034;,&#xD;
        SubsetQ[chordNotes, {octaveReduce[root + 10], octaveReduce[root + 7]}], &amp;#034;Dom7&amp;#034;,&#xD;
        SubsetQ[chordNotes, {octaveReduce[root + 10], octaveReduce[root + 6]}],  &amp;#034;d7&amp;#034;,&#xD;
        SubsetQ[ chordNotes, {octaveReduce[root + 9], octaveReduce[root + 6]}],  &amp;#034;d7d&amp;#034;,&#xD;
        SubsetQ[chordNotes, {octaveReduce[root + 10], octaveReduce[root + 3]}],  &amp;#034;m7&amp;#034;,&#xD;
        MemberQ[chordNotes, octaveReduce[root + 4]], &amp;#034;M&amp;#034;,&#xD;
        MemberQ[chordNotes, octaveReduce[root + 3]], &amp;#034;m&amp;#034;,&#xD;
        MemberQ[chordNotes, octaveReduce[root + 7]], &amp;#034;5&amp;#034;,&#xD;
        True, &amp;#034;undef&amp;#034;]}&#xD;
    ]&#xD;
&#xD;
&#xD;
###A note on notation&#xD;
In this project I use the following abbreviations for chord notation (they&amp;#039;re not in the standard format). &amp;#034;X&amp;#034; represents the root of the chord.&#xD;
&#xD;
 - *X-**5*** = undefined triad chord (just the root and the fifth)&#xD;
 - *X-**M*** = Major&#xD;
 - *X-**m*** = minor&#xD;
 - *X-**m7*** = minor triad with minor (a.k.a dominant) seventh&#xD;
 - *X-**d7d*** = fully diminished 7thchord&#xD;
 - *X-**d7*** = half diminished 7thchord&#xD;
 - *X-**Dom7*** = Dominant 7th chord&#xD;
 - *X-**7M*** = Major triad with Major 7th&#xD;
 - *X-**m7M*** = minor triad with Major 7th&#xD;
 - *X-**Dom9*** = Dominant 9th chord&#xD;
 - *X-**Dom9m*** = Dominant 7th chord with a minor 9th&#xD;
 - *X-**11*** = 11th chord&#xD;
 - *X-**13*** = 13th chord&#xD;
&#xD;
&#xD;
&#xD;
&#xD;
###Dealing with diminished 7th chords&#xD;
Now, on to `resolveDiminished7th`. What is this function on about?&#xD;
&#xD;
Well, recall the fully diminished seventh chords I mentioned in the Background section. Here&amp;#039;s the problem: they&amp;#039;re completely symmetrical! What I mean by that is that the intervals between subsequent notes are identical, even if you [invert][14] the chord. In other words, the distance in semitones between notes is constant (it&amp;#039;s 3) and is a factor of 12 (distance of 12 semitones = octave). So, given one of these chords, there is no way to determine which note is the root just by analyzing the chord itself. In the context of our algorithm, every note would have the same score!&#xD;
&#xD;
At this point I thought: &amp;#034;How do humans deal with this?&amp;#034;. And I concluded that the only way to resolve this issue is to have some contextual vision (looking at the next chord, particularly), which is how humans do it. So what `resolveDiminished7th` does is it brushes through the chord sequence stored in `result`, looking for fully diminished chords (marked with the string &amp;#034;d7d&amp;#034;), and re-assigns each of those a root by looking at the next chord:&#xD;
&#xD;
    resolveDiminished7th[chordSequence_List] := &#xD;
    Module[{result}, &#xD;
      result = Partition[chordSequence, 2, 1] /. {{nt_, &amp;#034;d7d&amp;#034;}, c2_List} :&amp;gt; Which[&#xD;
      MemberQ[octaveReduce /@ {nt, nt + 3, nt + 6, nt + 9}, octaveReduce[c2[[1]] - 1]], {{c2[[1]] - 1, &amp;#034;d7d&amp;#034;}, c2}, &#xD;
      MemberQ[octaveReduce /@ {nt, nt + 3, nt + 6, nt + 9}, octaveReduce[c2[[1]] + 4]], {{c2[[1]] + 4, &amp;#034;d7d&amp;#034;}, c2}, &#xD;
      MemberQ[octaveReduce /@ {nt, nt + 3, nt + 6, nt + 9}, octaveReduce[c2[[1]] + 6]], {{c2[[1]] + 6, &amp;#034;d7d&amp;#034;}, c2}, &#xD;
      True, {{nt, &amp;#034;d7d&amp;#034;}, c2}];&#xD;
      &#xD;
    result = Append[result[[All, 1]], Last[result][[2]]]&#xD;
    ]&#xD;
&#xD;
&#xD;
##Phase 4: Visualization&#xD;
&#xD;
Basically, my visualization function (`visualizeChordSequence`) is fundamentally a highly customized call of the `Graph` function; so I&amp;#039;ll just paste the code below and then explain what some parameters do:&#xD;
&#xD;
&#xD;
    visualizeChords[chordSequence_List, layoutSpec_String: &amp;#034;Unspecified&amp;#034;, version_String: &amp;#034;Full&amp;#034;, mVSize_: &amp;#034;Auto&amp;#034;, simplicitySpec_Integer: 0, normalizationSpec_String: &amp;#034;Softmax&amp;#034;] :=&#xD;
     Module[{purgedChordSequence, chordList, transitionRules, weights, graphicalWeights, nOfCases, edgeStyle, vertexLabels, vertexSize, vertexStyle, vertexShapeFunction, clip},&#xD;
      &#xD;
      &#xD;
      (*Preprocess*)&#xD;
      Switch[version, &#xD;
       &amp;#034;Full&amp;#034;, &#xD;
       purgedChordSequence = &#xD;
        StringJoin[toNoteName[#1], &amp;#034;-&amp;#034;, #2] &amp;amp; @@@ chordSequence,&#xD;
       &amp;#034;Basic&amp;#034;, &#xD;
       purgedChordSequence = &#xD;
        Split[toNoteName /@ chordSequence[[All, 1]]][[All, 1]]];&#xD;
      &#xD;
      &#xD;
      (*Amount of each chord*)&#xD;
      chordList = DeleteDuplicates[purgedChordSequence];&#xD;
      nOfCases = Table[{c, Count[purgedChordSequence, c]}, {c, chordList}];&#xD;
      &#xD;
      (*Transition rules between chords*)&#xD;
      Switch[version,&#xD;
       &amp;#034;Full&amp;#034;, &#xD;
       transitionRules = &#xD;
        Gather[Rule @@@ Partition[purgedChordSequence, 2, 1]],&#xD;
       &amp;#034;Basic&amp;#034;, &#xD;
       transitionRules =(*DeleteCases[*)&#xD;
        Gather[Rule @@@ Partition[purgedChordSequence, 2, 1]](*, t_/;&#xD;
       Length@t\[LessEqual]2]*) ];&#xD;
      &#xD;
      &#xD;
      (*Get processed weight for each transition*)&#xD;
      weights = Length /@ transitionRules;&#xD;
      If[normalizationSpec == &amp;#034;Softmax&amp;#034;, graphicalWeights = SoftmaxLayer[][weights]];;&#xD;
      graphicalWeights = &#xD;
       If[Min@graphicalWeights != Max@graphicalWeights, &#xD;
        Rescale[graphicalWeights, &#xD;
         MinMax@graphicalWeights, {0.003, 0.04}], &#xD;
        graphicalWeights /. _?NumericQ :&amp;gt; 0.03 ];&#xD;
      &#xD;
      (*Final transition list*)&#xD;
      transitionRules = transitionRules[[All, 1]];&#xD;
      &#xD;
      (*Graph display specs*)&#xD;
      clip = RankedMax[weights, 4];&#xD;
      &#xD;
      edgeStyle = &#xD;
       Table[(transitionRules[[i]]) -&amp;gt; &#xD;
         Directive[Thickness[graphicalWeights[[i]]], &#xD;
          Arrowheads[2.5 graphicalWeights[[i]] + 0.015], &#xD;
          Opacity[Which[&#xD;
            weights[[i]] &amp;lt;= Clip[simplicitySpec - 2, {0, clip - 2}], 0, &#xD;
            weights[[i]] &amp;lt;= Clip[simplicitySpec, {0, clip}], 0.2, &#xD;
            True, 0.6]], &#xD;
            RandomColor[Hue[_, 0.75, 0.7]], &#xD;
          Sequence @@ If[weights[[i]] &amp;lt;= Clip[simplicitySpec - 1, {0, clip - 1}], { &#xD;
             Dotted}, {}] ], {i, Length@transitionRules}];&#xD;
      &#xD;
      vertexLabels = &#xD;
       Thread[nOfCases[[All, &#xD;
          1]] -&amp;gt; (Placed[#, &#xD;
             Center] &amp;amp; /@ (Style[#[[1]], Bold, &#xD;
               Rescale[#[[2]], MinMax[nOfCases[[All, 2]]], &#xD;
                Switch[mVSize, &amp;#034;Auto&amp;#034;, {6, 20}, _List, &#xD;
                 10*mVSize[[1]]/0.3*{1, mVSize[[2]]/mVSize[[1]]}]]] &amp;amp; /@ &#xD;
             nOfCases))];&#xD;
      &#xD;
      vertexSize = &#xD;
       Thread[nOfCases[[All, 1]] -&amp;gt; &#xD;
         Rescale[nOfCases[[All, 2]], MinMax[nOfCases[[All, 2]]], &#xD;
          Switch[mVSize, &#xD;
           &amp;#034;Auto&amp;#034;, (Floor[Length@chordList/10] + 1)*{0.1, 0.3}, _List, &#xD;
           mVSize]]];&#xD;
      &#xD;
      vertexStyle = &#xD;
       Thread[nOfCases[[All, 1]] -&amp;gt; &#xD;
         Directive[Hue[0.53, 0.27, 1, 0.6], EdgeForm[Blue]]];&#xD;
      &#xD;
      vertexShapeFunction = &#xD;
       Switch[version, &amp;#034;Full&amp;#034;, Ellipsoid[#1, {3.5, 1} #3] &amp;amp;, &amp;#034;Basic&amp;#034;, &#xD;
        Ellipsoid[#1, {2, 1} #3] &amp;amp;];&#xD;
      &#xD;
      &#xD;
      &#xD;
      &#xD;
      Graph[transitionRules, &#xD;
       &#xD;
       GraphLayout -&amp;gt; &#xD;
        Switch[layoutSpec, &amp;#034;Unspecified&amp;#034;, Automatic, _, layoutSpec],&#xD;
       &#xD;
       EdgeStyle -&amp;gt; edgeStyle,&#xD;
       EdgeWeight -&amp;gt; weights,&#xD;
       VertexLabels -&amp;gt; vertexLabels,&#xD;
       VertexSize -&amp;gt; vertexSize,&#xD;
       VertexStyle -&amp;gt; vertexStyle,&#xD;
       VertexShapeFunction -&amp;gt; vertexShapeFunction,&#xD;
       PerformanceGoal -&amp;gt; &amp;#034;Quality&amp;#034;]&#xD;
      ]&#xD;
&#xD;
There are five main things to focus on in the above definition: the graph layout (passed as the argument `layoutSpec`), the edge thickness (defined in `edgeStyle`), the vertex size (defined in `vertexSize`), the version (passed as argument `version`) and the simplicity specification (`simplicitySpec`).&#xD;
&#xD;
The graph layout is a `Graph` option that can be specified in the argument `layoutSpec`. If `&amp;#034;Unspecified&amp;#034;` is passed, an automatic layout will be used. I find that the best layouts tend to be, in order of preference, &amp;#034;BalloonEmbedding&amp;#034; and &amp;#034;RadialEmbedding&amp;#034;; nevertheless, neither are a perfect fit for every piece. In the future I would like to to implement custom (i.e. pre-defined) positioning, so that I can design it in a way that best fits this project.&#xD;
&#xD;
The edge thickness is a function of the amount of times a certain transition between two chords has occurred in the chord sequence. There is an option (namely the `normalizationSpec` argument) to enable or disable using a Softmax function for assigning thicknesses to edges. This is due to the fact that for simple/short chord sequences, Softmax is actually counterproductive because it suppresses secondary but still top-ranked transitions; i.e., it assigns a very high thickness to the most frequent transition and a low thickness to all other transitions (even those that come in second or third in frequency ranking). But for large or complex sequences it is actually useful, because it &amp;#034;gets rid of&amp;#034; a lot of the \[relatively\] insignificant instances, thus making the output actually understandable (and not just a [jumbled mess of thick lines][15]).&#xD;
&#xD;
The vertex size is proportional to the number of occurrences of each particular chord (that is, without taking into account the transitions). It can also be specified manually by passing `vSize` as a list `{a,b}` such that `a` is the minimum size an `b` is the maximum.&#xD;
&#xD;
The `version` can be either `&amp;#034;Full&amp;#034;` or `&amp;#034;Basic&amp;#034;`; the default is `&amp;#034;Full&amp;#034;`. The `&amp;#034;Basic&amp;#034;` version consists of a simplified chord set in which only the root note of the chord is taken into account, and not the archetype. For example, all C chords (M, Dom7, m...) would be represented by a single `&amp;#034;C&amp;#034;` vertex.&#xD;
&#xD;
Finally, the simplicity specification (`simplicitySpec`) is a number that can be thought of, in some way, as a &amp;#034;noise&amp;#034; threshold: as it gets larger, fewer edges &amp;#034;stand out&amp;#034;that is, more of the lower-significance ones are rendered with reduced opacity or are shown as dotted lines. This is useful for large or complex sequences.&#xD;
&#xD;
&amp;lt;br&amp;gt;&#xD;
&#xD;
&#xD;
----------&#xD;
&#xD;
&#xD;
#Some examples&#xD;
&#xD;
Here I will show some specific examples generated with this tool. I tried to use different styles of music for comparison.&#xD;
&#xD;
 - **Bach**&amp;#039;s [prelude no.1][16] from the Well Tempered Clavier:&#xD;
&#xD;
![Visualization of Bach&amp;#039;s prelude no.1 ][17]&#xD;
 &#xD;
  - **Debussy**&amp;#039;s [*Passepied*][18] from the *Suite Bergamasque*:&#xD;
&#xD;
![Visualization of Debussy&amp;#039;s *Passepied*][19]&#xD;
&#xD;
 - A &amp;#034;template&amp;#034; blues progression:&#xD;
&#xD;
![Blues template][20]&#xD;
&#xD;
 - **Beethoven**&amp;#039;s second movement from the *Pathétique* sonata (no.8):&#xD;
&#xD;
![Beethoven][21]&#xD;
&#xD;
 - Any &amp;#034;reggaeton&amp;#034; song (e.g. Despacito):&#xD;
&#xD;
![Reggaeton][22]&#xD;
&#xD;
#Microsite&#xD;
&#xD;
Check out the form page (a.k.a. microsite) of this project [here][23]:&#xD;
&#xD;
https://www.wolframcloud.com/objects/lammenspaolo/Chord%20sequence%20visualization&#xD;
&#xD;
[![enter image description here][24]][23]&#xD;
&#xD;
Briefly, here is what each option does (see the section **Algorithms and code** for a more detailed explanation):&#xD;
&#xD;
 - **Chunkifier funciton**: choose between splitting notes by measures or by a constant amount of notes&#xD;
 - **Measure split factor**: choose into how many pieces you want to divide measures (each piece will be analyzed as a separate chord)&#xD;
 - **Graph layout**: choose the layout option for the `Graph` call&#xD;
 - **Normalization function**: choose whether to apply a Softmax function to the weights of edges (to make results clearer in case of complex sequences).&#xD;
 - **Version**: choose &amp;#034;Full&amp;#034; for complete chord info (e.g. &amp;#034;C-M&amp;#034;, &amp;#034;D-Dom7&amp;#034;, &amp;#034;C-7M&amp;#034;...) or &amp;#034;Basic&amp;#034; for just the root of the chord (e.g. &amp;#034;C&amp;#034;, &amp;#034;D&amp;#034;...)&#xD;
 - **Vertex size**: specify vertex size as a list `{a,b}` where `a` is the minimum and `b` is the maximum size&#xD;
 - **Simplicity parameter**: visual simplification of the graph (a value of 0 means no simplification is applied)&#xD;
&#xD;
&amp;lt;br&amp;gt;&#xD;
&#xD;
#Conclusions&#xD;
I have developed a functional tool to visualize chord sequences as graphs. It is far from perfect, though. In the future, I would like improving the positioning of vertices, being able to eliminate insignificant transitions from the graph altogether, and making other visual adjustments. Furthermore, I plan to refine and optimize the chord analyzer, as right now it is just an experimental version that isn&amp;#039;t too accurate. A better &amp;#034;chunkifier&amp;#034; function could be developed too.&#xD;
&#xD;
Finally, I&amp;#039;d like to thank my mentor Christian Pasquel and all of the other WSC staff for this amazing opportunity. I&amp;#039;d also like to thank my music theory teacher, Raimon Romaní, for making me, over the years, sufficiently less terrible at musical analysis to be able to undertake this project.&#xD;
&#xD;
&#xD;
  [1]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Prelude.png&amp;amp;userId=1372342&#xD;
  [2]: https://en.wikipedia.org/wiki/Markov_chain &amp;#034;Wikipedia: Markov chain&amp;#034;&#xD;
  [3]: https://en.wikipedia.org/wiki/Interval_(music) &amp;#034;Wikipedia: Interval&amp;#034;&#xD;
  [4]: https://en.wikipedia.org/wiki/Atonality &amp;#034;Wikipedia: Atonality&amp;#034;&#xD;
  [5]: https://youtu.be/L85XTLr5eBE &amp;#034;Schönberg&amp;#039;s 4th string quartet on YouTube&amp;#034;&#xD;
  [6]: https://en.wikipedia.org/wiki/Tonic_%28music%29 &amp;#034;Wikipedia: Tonic&amp;#034;&#xD;
  [7]: http://astronomy.swin.edu.au/cosmos/S/Schwarzschild+Radius &amp;#034;Basic info on Schwartzschild radius&amp;#034;&#xD;
  [8]: https://en.wikipedia.org/wiki/Dominant_(music) &amp;#034;Dominant chord&amp;#034;&#xD;
  [9]: http://community.wolfram.com//c/portal/getImageAttachment?filename=2548Macro_analysis_chords_on_C.jpg&amp;amp;userId=1372342&#xD;
  [10]: https://en.wikipedia.org/wiki/Seventh_chord &amp;#034;Wikipedia: Seventh chord&amp;#034;&#xD;
  [11]: https://en.wikipedia.org/wiki/Interval_(music) &amp;#034;Wikipedia: Interval&amp;#034;&#xD;
  [12]: https://en.wikipedia.org/wiki/Dominant_seventh_chord &amp;#034;Wikipedia: Dominant seventh&amp;#034;&#xD;
  [13]: http://community.wolfram.com//c/portal/getImageAttachment?filename=images.png&amp;amp;userId=1372342&#xD;
  [14]: https://en.wikipedia.org/wiki/Inversion_(music)#Chords &amp;#034;Wikipedia: Inversion#Chords&amp;#034;&#xD;
  [15]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Passepied.png&amp;amp;userId=1372342 &amp;#034;Jumbled mess!&amp;#034;&#xD;
  [16]: https://www.youtube.com/watch?v=aengbLEFnM8&#xD;
  [17]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Prelude.png&amp;amp;userId=1372342&#xD;
  [18]: https://www.youtube.com/watch?v=hDWbVP-5DSA &amp;#034;Passepied&amp;#034;&#xD;
  [19]: http://community.wolfram.com//c/portal/getImageAttachment?filename=deb_pass2.png&amp;amp;userId=1372342&#xD;
  [20]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Blues.png&amp;amp;userId=1372342&#xD;
  [21]: http://community.wolfram.com//c/portal/getImageAttachment?filename=pathetique.png&amp;amp;userId=1372342&#xD;
  [22]: http://community.wolfram.com//c/portal/getImageAttachment?filename=Reggaeton.png&amp;amp;userId=1372342&#xD;
  [23]: https://www.wolframcloud.com/objects/lammenspaolo/Chord%20sequence%20visualization &amp;#034;Microsite&amp;#034;&#xD;
  [24]: http://community.wolfram.com//c/portal/getImageAttachment?filename=ScreenShot2018-07-19at1.53.02PM.png&amp;amp;userId=11733</description>
    <dc:creator>Paolo Lammens</dc:creator>
    <dc:date>2018-07-14T05:10:03Z</dc:date>
  </item>
  <item rdf:about="https://community.wolfram.com/groups/-/m/t/3299985">
    <title>[BOOK] Signals, systems, and signal processing: a computational approach</title>
    <link>https://community.wolfram.com/groups/-/m/t/3299985</link>
    <description>![Signals, systems, and signal processing: a computational approach][1]&#xD;
&#xD;
&amp;amp;[Wolfram Notebook][2]&#xD;
&#xD;
&#xD;
  [1]: https://community.wolfram.com//c/portal/getImageAttachment?filename=Main18102024.png&amp;amp;userId=20103&#xD;
  [2]: https://www.wolframcloud.com/obj/9fef1db9-ca5d-4080-9db5-fefdbb4d3085</description>
    <dc:creator>Mariusz Jankowski</dc:creator>
    <dc:date>2024-10-17T21:55:31Z</dc:date>
  </item>
</rdf:RDF>

