Beefy Boxes and Bandwidth Generously Provided by pair Networks
Problems? Is your data what you think it is?

Design for converting between musical formats ?

by benn (Vicar)
on Aug 12, 2003 at 11:16 UTC ( #283141=perlquestion: print w/replies, xml ) Need Help??
benn has asked for the wisdom of the Perl Monks concerning the following question:

Greetings Brethren,

I'm about to plunge into some code to convert various musical note formats back and forth - "BB-" <->"Bb2" <->"bf3" etc. Looking around, I guess there are between 5 and 10 different formats that I'll eventually want to build in.

My problem is how to structure this. Possible options would appear to be...

  • Provide (up to 100!) different methods for each conversion (ugh). More work for me, but with a consistent naming scheme (abc2kern(), kern2midi(), midi2abc() etc.), possible easier for the user - a simple list of format names would provide every possible method name.
  • As above, but use AUTOLOAD or similar to 'generate' the method - split up the method name and call "convert($1,$2,$argument)"
  • All passed as parameters to a single method - convert("BB-","kern","abc").
  • As above, but 'autodetect' the original style - convert_to("BB-","abc") - slightly problematic, but possible.
  • Named param style - convert(note=>"BB-",from=>'kern",to=>"abc")
  • OO style - notetype->new("BB-","kern")->convert_to("abc).
  • 'No param' OO style - notetype->new("BB-","kern")->as_abc()
  • Use package variables to set defaults - $::INPUT="kern"; $::OUTPUT="abc"; convert("BB-");
  • {Fill in your own favourite here :) }
...and I'm sure there are many others :). As this is intended for a CPAN module rather than supporting any specific piece of code, I have no 'in-house' style guidelines to follow, and I don't really know how potential users will want to use the module (or even if there *are* any potential users except for myself :) ), so want to make it as intuitive and consistent as possible. I guess that it'll most often be called as part of a loop in code that'll only be dealing with single 'from' and 'to' formats - hence the package default idea ( so that I'm not having to read/parse the format types for every call).

One wrinkle is that different formats may require / return additional parameters - ABC format, for instance, sets up a key and a default octave as part of its header, so they may need to be passed in ("F" in the key "D" would convert to "F#" etc.).

Atm, I'm favouring the named parameter style (easy to maintain and pass extra parameters ) but I'd be grateful for any input before I "get my coding pencil out" :)


Title edit by tye

  • Comment on Design for converting between musical formats ?

Replies are listed 'Best First'.
Re: A Matter of Style...
by Skeeve (Vicar) on Aug 12, 2003 at 11:27 UTC
    Hmmm... I wouldn't use it, as I don't deal with musical notes in any way.

    Nevertheless I don't think you need any "convert-from-to" routines.

    What I think you would need is:

    1. an internal representation of musical notes
    2. a routine to read some notations into your represantation
    3. a routine to write your notes in some notation
    So the only "conversions" would be done from any notation to your internal representation and back. You won't need n*n-n routines but just 2*n.

Re: A Matter of Style...
by Juerd (Abbot) on Aug 12, 2003 at 11:27 UTC

    'No param' OO style - notetype->new("BB-","kern")->as_abc()

    I like that one best. I'd just convert everything to an internal format on object creation, though. SomeClass->new(type => "notetype", ...)->as_abc. From there, you can create very simple wrappers for people who like different methods better, so everyone can have it their way.

    Juerd # { site => '', plp_site => '', do_not_use => 'spamtrap' }

Re: A Matter of Style...
by dragonchild (Archbishop) on Aug 12, 2003 at 13:06 UTC
    Skeeve is absolutely correct in his statement. I would recommend the following:
    1. Pick a representation to use internally. I would make one up, probably along the lines of:
      • Key
      • Octave (from some default ... can be negative)
      • Note number
      The point here is to make it easy for you to do manipulation on the note.
    2. Figure out how to convert between your representation and some other representation
    3. Encapsulate that knowledge in some object that is different from your note representation. Have a Converter that will take a Note and return a string or take a string and return a Note.

    The way to think about this is to consider Date::Calc or Date::Manip, two standard date manipulation modules. You give them a date string in pretty much any format and they will parse it. You can then manipulate it in nearly any way you can think of. You can then ask for the date back in pretty much any format.

    The point here is that Date::Calc doesn't store weekdays as Monday, Tuesday, etc. It stores them as 1, 2, etc. But, it knows how to convert Day 1 to Monday (or lundi, or Mon, or whatever.), or vice versa. That's what you should strive for.

    We are the carpenters and bricklayers of the Information Age.

    The idea is a little like C++ templates, except not quite so brain-meltingly complicated. -- TheDamian, Exegesis 6

    Please remember that I'm crufty and crochety. All opinions are purely mine and all code is untested, unless otherwise specified.

Re: A Matter of Style...
by fglock (Vicar) on Aug 12, 2003 at 12:37 UTC
      Thank you - this was the 'looking around' to which I referred :) It was after finding Gerd's site that I narrowed the list down to 'between 5 and 10' :)


Re: A Matter of Style...
by benn (Vicar) on Aug 12, 2003 at 14:09 UTC
    /me slaps himself aound the head with an overgrown steriod-pumped trout

    Doh! Yes indeed. This is all part of an ongoing discussion about how stuff should be represented in the Music:: namespace, once I get around to writing Music::Chord and Music::Keysignature etc. I'd so far been going with ISO format for input/output, just because it looked nicer :)

    Thinking just a little into the future though (I *must* get into the habit of doing that :) ), it'd make a lot more sense if eveything dealt with Music::Note objects - I then get to do all the cool functions like $note->transpose(), $note->enharmonic_equivalent('natural') and $note->is_jazz_accidental_and_not_a_mistake().

    Thanks all - I knew that posting would save me days of re-coding :)


Log In?

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://283141]
Approved by Skeeve
Discipulus when naming is clear and you know how to arrange the data, then coding it is a mere writing work
[Lady_Aleena]: marioroy, welcome to my insanity. 8)
marioroy likes Dragod, an unbelievably huge dragon. It is bigger than any planet. Wow.
[Lady_Aleena]: marioroy, not my creation, it was submitted a long long time ago when I had submission forms with a form script I can't remember the name of off the top of my head.

How do I use this? | Other CB clients
Other Users?
Others scrutinizing the Monastery: (9)
As of 2017-05-29 09:14 GMT
Find Nodes?
    Voting Booth?