// // Programmer: Craig Stuart Sapp // Creation Date: Sat Jun 9 14:48:41 PDT 2001 // Last Modified: Sun Jun 20 13:35:41 PDT 2010 added rational rhythms // Last Modified: Wed Jan 26 18:14:20 PST 2011 added --debug // Last Modified: Tue Apr 12 12:04:23 PDT 2011 fixed findlcm for rational rhys. // Filename: ...museinfo/examples/all/minrhy.cpp // Web Address: http://sig.sapp.org/examples/museinfo/humdrum/minrhy.cpp // Syntax: C++; museinfo // // Description: calculates the minimum timebase which is the least common // multiple of all rhythms in the file. // // Todo: some things to clean up in rhythmic representation due to conversions // from ints to RationalNumber class for rhythms/durations... #include "humdrum.h" // function declarations void checkOptions (Options& opts, int argc, char* argv[]); void example (void); void usage (const char* command); int findlcm (Array& list); int findlcmR (Array& list); int GCD (int a, int b); void insertRhythm (Array& allrhythms, RationalNumber value); void sortArray (Array& rhythms); int ratcomp (const void* a, const void* b); template void uniqArray(Array& array); // global variables Options options; // database for command-line arguments int listQ = 0; // used with -l option int debugQ = 0; // used with --debug /////////////////////////////////////////////////////////////////////////// int main(int argc, char** argv) { checkOptions(options, argc, argv); HumdrumFile hfile; Array timebase; RationalNumber zeroR(0, 1); timebase.setSize(argc-1); timebase.setAll(zeroR); timebase.allowGrowth(0); Array rhythms; Array allrhythms; allrhythms.setSize(100); allrhythms.setSize(0); allrhythms.setGrowth(1000); int i, j; // figure out the number of input files to process int numinputs = options.getArgCount(); // can't handle standard input yet for (i=1; i<=numinputs; i++) { hfile.clear(); hfile.read(options.getArg(i)); hfile.analyzeRhythm(); if (numinputs > 1) { cout << argv[i] << ":\t"; } if (listQ) { hfile.getRhythms(rhythms); sortArray(rhythms); uniqArray(rhythms); for (j=0; j 1) { if (listQ) { cout << "all:\t"; for (j=0; j& rhythms) { qsort(rhythms.getBase(), rhythms.getSize(), sizeof(RationalNumber), ratcomp); } ////////////////////////////// // // uniqArray -- filter out adjacent duplicate elements. // template void uniqArray(Array& array) { Array newarray(array.getSize()); newarray.setSize(0); if (array.getSize() <= 1) { // nothing to do return; } newarray.append(array[0]); int i; for (i=1; i *((RationalNumber*)b)) { return 1; } else { return 0; } } /////////////////////////////////////////////////////////////////////////// ////////////////////////////// // // insertRhythm -- // void insertRhythm(Array& allrhythms, RationalNumber value) { int i; for (i=0; i& rhythms) { if (rhythms.getSize() == 0) { return 0; } int output = rhythms[0]; for (int i=1; i& rhythms) { if (rhythms.getSize() == 0) { return 0; } Array plain; plain.setSize(rhythms.getSize()); int i; for (i=0; i