Refactor IsPowerOfTwo determination

This commit is contained in:
Matthias Neeracher 2011-09-12 16:17:21 +02:00
parent e32c253870
commit 23ced3e860
6 changed files with 17 additions and 9 deletions

View File

@ -294,7 +294,7 @@ void VLLilypondWriter::VisitChord(VLChord & c)
if (name == "r") if (name == "r")
name = "s"; name = "s";
char duration[16]; char duration[16];
if (c.fDuration.fNum == 1 && !(c.fDuration.fDenom & (c.fDuration.fDenom-1))) // Power of two if (c.fDuration.IsPowerOfTwo())
sprintf(duration, "%d", c.fDuration.fDenom); sprintf(duration, "%d", c.fDuration.fDenom);
else else
sprintf(duration, "1*%d/%d", c.fDuration.fNum, c.fDuration.fDenom); sprintf(duration, "1*%d/%d", c.fDuration.fNum, c.fDuration.fDenom);

View File

@ -117,7 +117,7 @@ void VLMMAWriter::VisitNote(VLLyricsNote & n)
char buf[4]; char buf[4];
std::string dur; std::string dur;
if (n.fDuration.fNum == 1) if (n.fDuration.fNum == 1)
if (!(n.fDuration.fDenom & (n.fDuration.fDenom-1))) { if (n.fDuration.IsPowerOfTwo()) {
sprintf(buf, "%d", n.fDuration.fDenom); sprintf(buf, "%d", n.fDuration.fDenom);
dur = buf; dur = buf;
} else if (n.fDuration.fDenom == 3) { } else if (n.fDuration.fDenom == 3) {

View File

@ -78,6 +78,15 @@ VLFraction & VLFraction::operator%=(VLFraction other)
return *this *= other; return *this *= other;
} }
bool VLFraction::IsPowerOfTwo() const
{
//
// !(x & (x-1)) is true if x had only a single bit set and thus
// is a power of two. We're not really interested in the case >1
//
return fNum == 1 && !(fDenom & (fDenom-1));
}
#pragma mark - #pragma mark -
#pragma mark class VLNote #pragma mark class VLNote
@ -114,10 +123,7 @@ void VLNote::MakeRepresentable()
fVisual = kWhole | (fVisual & kAccidentalsMask); fVisual = kWhole | (fVisual & kAccidentalsMask);
VLFraction part(1,1); VLFraction part(1,1);
VLFraction triplet(2,3); VLFraction triplet(2,3);
// bool nonTriplet = fDuration.IsPowerOfTwo();
// Power of 2 denominators are not triplets
//
bool nonTriplet(!(fDuration.fDenom & (fDuration.fDenom-1)));
while (part.fDenom < 64) { while (part.fDenom < 64) {
if (fDuration >= part) { if (fDuration >= part) {
fDuration = part; fDuration = part;

View File

@ -36,6 +36,8 @@ struct VLFraction : VLFract {
VLFraction & operator%=(VLFraction other); VLFraction & operator%=(VLFraction other);
VLFraction & Normalize(); VLFraction & Normalize();
bool IsPowerOfTwo() const;
}; };
inline float operator*(VLFraction f, float sc) inline float operator*(VLFraction f, float sc)

View File

@ -202,7 +202,7 @@ void VLPlistVisitor::VisitNote(VLLyricsNote & n)
// 4th 4th 8th // 4th 4th 8th
// //
[nd setObject:[NSNumber numberWithInt:fTupletNote] forKey:@"normalType"]; [nd setObject:[NSNumber numberWithInt:fTupletNote] forKey:@"normalType"];
if (fTupletDur.fNum == 1 && !(fTupletDur.fDenom&(fTupletDur.fDenom-1))) if (fTupletDur.IsPowerOfTwo())
fInTuplet = 0; fInTuplet = 0;
} }
} else if (fInTuplet == tupletNum) } else if (fInTuplet == tupletNum)

View File

@ -388,8 +388,8 @@
} }
++inTuplet; ++inTuplet;
tupletDur += note->fDuration / VLNote::TupletDenom(tuplet); tupletDur += note->fDuration / VLNote::TupletDenom(tuplet);
if (tuplet == VLNote::kTriplet ? (tupletDur.fNum == 1 && !(tupletDur.fDenom & (tupletDur.fDenom-1))) if (tuplet == VLNote::kTriplet
: inTuplet == VLNote::TupletNum(tuplet) ? tupletDur.IsPowerOfTwo() : inTuplet == VLNote::TupletNum(tuplet)
) { ) {
// //
// Tuplet adds up to power of two fraction // Tuplet adds up to power of two fraction