comparison Syncopation models/PRS.py @ 12:4acddc008048

Revised LHL and PRS model's argument list; refactored the variable names
author csong <csong@eecs.qmul.ac.uk>
date Fri, 03 Apr 2015 16:38:32 +0100
parents 031e2ccb1fb6
children 9030967a05f8
comparison
equal deleted inserted replaced
9:c2843ef4de2c 12:4acddc008048
1 ''' 1 '''
2 Author: Chunyang Song 2 Author: Chunyang Song
3 Institution: Centre for Digital Music, Queen Mary University of London 3 Institution: Centre for Digital Music, Queen Mary University of London
4 ''' 4 '''
5 5
6 from BasicFuncs import repeat, subdivide, ceiling, get_min_timeSpan 6 from basic_functions import repeat, subdivide, ceiling, get_min_timeSpan, get_rhythm_category
7 7
8 def get_cost(seq,next_seq): 8 def get_cost(sequence,nextSequence):
9 seq = get_min_timeSpan(seq) # converting to the minimum time-span format 9 sequence = get_min_timeSpan(sequence) # converting to the minimum time-span format
10 10
11 if seq[1:] == repeat([0],len(seq)-1): # null prototype 11 if sequence[1:] == repeat([0],len(sequence)-1): # null prototype
12 cost = 0 12 cost = 0
13 elif seq == repeat([1],len(seq)): # filled prototype 13 elif sequence == repeat([1],len(sequence)): # filled prototype
14 cost = 1 14 cost = 1
15 elif seq[0] == 1 and seq[-1] == 0: # run1 prototype 15 elif sequence[0] == 1 and sequence[-1] == 0: # run1 prototype
16 cost = 2 16 cost = 2
17 elif seq[0] == 1 and (next_seq == None or next_seq[0] == 0): # run2 prototype 17 elif sequence[0] == 1 and (nextSequence == None or nenextSequencext_seq[0] == 0): # run2 prototype
18 cost = 2 18 cost = 2
19 elif seq[0] == 1 and seq[-1] == 1 and next_seq != None and next_seq[0] == 1: # upbeat prototype 19 elif sequence[0] == 1 and sequence[-1] == 1 and nextSequence != None and nextSequence[0] == 1: # upbeat prototype
20 cost = 3 20 cost = 3
21 elif seq[0] == 0: # syncopated prototype 21 elif sequence[0] == 0: # syncopated prototype
22 cost = 5 22 cost = 5
23 23
24 return cost 24 return cost
25 25
26 # This function calculates the syncopation value (cost) for the sequence with the postbar_seq for a certain level. 26 # This function calculates the syncopation value (cost) for the sequence with the postbar_seq for a certain level.
27 def syncopation_perlevel(sub_seqs, num_subs): 27 def syncopation_perlevel(subSequences):
28 total = 0 28 total = 0
29 for l in range(num_subs): 29 for l in range(len(subSequences)-1):
30 total = total + get_cost(sub_seqs[l], sub_seqs[l+1]) 30 total = total + get_cost(subSequences[l], subSequences[l+1])
31 normalised = float(total)/num_subs 31 normalised = float(total)/(len(subSequences)-1)
32 32
33 return normalised 33 return normalised
34 34
35 # This function calculates the overall syncopation value for a bar of sequence.. 35 #def get_syncopation(seq,subdivision_seq, postbar_seq, rhythm_category):
36 def get_syncopation(seq,subdivision_seq, postbar_seq, rhythm_category): 36 def get_syncopation(bar, weightSequence = None, LMax = None):
37 '''
38 The get_syncopation function calculates the overall syncopation value for a bar of sequence.
39 '''
37 syncopation = None 40 syncopation = None
38 if rhythm_category == 'poly': 41
39 print 'Error: PRS model cannot deal with polyrhythms.' 42 binarySequence = bar.get_binary_sequence()
43 subdivisionSequence = bar.get_subdivision_sequence()
44
45 if get_rhythm_category(binarySequence, subdivisionSequence) == 'poly':
46 print 'Warning: PRS model detects polyrhythms so returning None.'
40 else: 47 else:
41 syncopation = 0 48 syncopation = 0
42 49
43 current_num_subs = 1 # the initial number of sub-sequences at a certain metrical level 50 if bar.get_next_bar() != None:
44 for subdivisor in subdivision_seq: 51 nextbarBinarySequence = bar.get_next_bar().get_binary_sequence()
52 else:
53 nextbarBinarySequence = None
54
55 # the initial number of sub-sequences at a certain metrical level
56 numberOfSubSeqs = 1
57 for subdivisor in subdivisionSequence:
45 # the number of sub-sequence at the current level is product of all the subdivisors up to the current level 58 # the number of sub-sequence at the current level is product of all the subdivisors up to the current level
46 current_num_subs = current_num_subs * subdivisor 59 numberOfSubSeqs = numberOfSubSeqs * subdivisor
47 # recursion stops when the length of sub-sequence is less than 2 60 # recursion stops when the length of sub-sequence is less than 2
48 if len(seq)/current_num_subs >= 2: 61 if len(binarySequence)/numberOfSubSeqs >= 2:
49 # generate sub-sequences and append the next bar sequence 62 # generate sub-sequences and append the next bar sequence
50 sub_seqs = subdivide(ceiling(seq), current_num_subs) 63 subSequences = subdivide(ceiling(binarySequence), numberOfSubSeqs)
51 sub_seqs.append(postbar_seq) 64 subSequences.append(nextbarBinarySequence)
52 # adding syncopation at each metrical level to the total syncopation 65 # adding syncopation at each metrical level to the total syncopation
53 syncopation += syncopation_perlevel(sub_seqs, current_num_subs) 66 syncopation += syncopation_perlevel(subSequences)
54 else: 67 else:
55 break 68 break
56 69
57 return syncopation 70 return syncopation