diff --git a/rpn/makeHelp.py b/rpn/makeHelp.py index 264906a..cbb38f7 100644 --- a/rpn/makeHelp.py +++ b/rpn/makeHelp.py @@ -55,7 +55,7 @@ PROGRAM_NAME = 'makeHelp' PROGRAM_DESCRIPTION = 'rpnChilada help generator' -MAX_EXAMPLE_COUNT = 2451 # This needs to be manually updated when the help examples are modified. +MAX_EXAMPLE_COUNT = 2458 # This needs to be manually updated when the help examples are modified. os.chdir( getUserDataPath( ) ) # SkyField doesn't like running in the root directory @@ -8383,14 +8383,26 @@ def makeCommandExample( command, indent=0, slow=False ): [ 'is_k_morphic', 'is_trimorphic', 'is_kaprekar' ] ], 'is_base_k_pandigital' : [ -'lexicography', 'returns whether n a pandigital number in base k', +'lexicography', 'returns whether n a pandigital number in base k, not counting 0', +''' +This boolean operator returns whether n is a pandigital number in base k, not +counting the digit 0. The presence or abscence of 0 does not affect this +operator, only digits 1 through k. +''', +''' +''' + makeCommandExample( '12345678 -b9' ) + ''' +''' + makeCommandExample( '6053444 9 is_base_k_pandigital' ), +[ 'is_base_k_pandigital_zero, is_pandigital', 'is_pandigital_zero' ] ], + + 'is_base_k_pandigital_zero' : [ +'lexicography', 'returns whether n a pandigital number in base k, including 0', ''' This boolean operator returns whether n is a pandigital number in base k. ''', ''' ''' + makeCommandExample( '123456780 -b9' ) + ''' ''' + makeCommandExample( '54480996 9 is_base_k_pandigital' ), -[ 'is_pandigital' ] ], +[ 'is_base_k_pandigital, is_pandigital', 'is_pandigital_zero' ] ], 'is_base_k_smith_number' : [ 'lexicography', 'returns whether n is a Smith number in base k', @@ -8452,7 +8464,7 @@ def makeCommandExample( command, indent=0, slow=False ): ''' + makeCommandExample( '101 110 is_digital_permutation' ) + ''' ''' + makeCommandExample( '1234 4321 is_digital_permutation' ) + ''' ''' + makeCommandExample( '1201 1201 is_digital_permutation' ), -[ 'is_pandigital', 'permute_digits' ] ], +[ 'is_pandigital', 'is_pandigital_zero', 'permute_digits' ] ], 'is_generalized_dudeney' : [ 'lexicography', 'returns whether an integer n is a generalized Dudeney number of power k', @@ -8612,16 +8624,28 @@ def makeCommandExample( command, indent=0, slow=False ): [ 'find_palindrome', 'is_pandigital', 'is_increasing', 'is_decreasing' ] ], 'is_pandigital' : [ -'lexicography', 'returns whether an integer n is pandigital', +'lexicography', 'returns whether an integer n is pandigital, not counting 0', ''' -A pandigital number contains at least one of all the of the digits 0 through -9. +A pandigital number contains at least one of all the of the digits 1 through +9. Zeroes are ignored. ''', ''' ''' + makeCommandExample( '123456789 is_pandigital' ) + ''' ''' + makeCommandExample( '1234567890 is_pandigital' ) + ''' ''' + makeCommandExample( '-a30 [ 3 3 7 19 928163 1111211111 ] prod is_pandigital' ), -[ 'is_base_k_pandigital', 'is_digital_palindrome', 'is_increasing', 'is_decreasing' ] ], +[ 'is_pandigital_zero', 'is_base_k_pandigital', 'is_digital_palindrome', 'is_increasing', 'is_decreasing' ] ], + + 'is_pandigital_zero' : [ +'lexicography', 'returns whether an integer n is pandigital, including 0', +''' +A pandigital number contains at least one of all the of the digits 0 through +9. +''', +''' +''' + makeCommandExample( '123456789 is_pandigital_zero' ) + ''' +''' + makeCommandExample( '1234567890 is_pandigital_zero' ) + ''' +''' + makeCommandExample( '-a30 [ 3, 3, 3, 3, 37, 37, 333667, 333667 ] prod is_pandigital_zero' ), +[ 'is_pandigital', 'is_base_k_pandigital', 'is_digital_palindrome', 'is_increasing', 'is_decreasing' ] ], 'is_pdi' : [ 'lexicography', 'returns whether an integer n is a perfect digital invariant', diff --git a/rpn/math/rpnLexicographic.py b/rpn/math/rpnLexicographic.py index 51db125..925277f 100644 --- a/rpn/math/rpnLexicographic.py +++ b/rpn/math/rpnLexicographic.py @@ -158,6 +158,27 @@ def isBaseKPandigitalOperator( n, base ): return 1 +#****************************************************************************** +# +# isBaseKPandigitalZeroOperator +# +#****************************************************************************** + +@twoArgFunctionEvaluator( ) +@argValidator( [ IntValidator( ), IntValidator( 2 ) ] ) +def isBaseKPandigitalZeroOperator( n, base ): + digits = convertToBaseN( n, base, outputBaseDigits=True ) + + for i in arange( 1, min( int( base ), len( digits ) ) ): + try: + digits.index( i ) + except ValueError: + return 0 + + return 1 + + + #****************************************************************************** # # sumDigitsOperator @@ -392,10 +413,10 @@ def isPandigital( n ): length = len( n ) - if length < 10: + if length < 9: return 0 - digitsToCheck = string.digits + digitsToCheck = string.digits[ 1 : ] for c in digitsToCheck: if c not in n: @@ -410,6 +431,35 @@ def isPandigitalOperator( n ): return isPandigital( n ) +#****************************************************************************** +# +# isPandigitalZeroOperator +# +#****************************************************************************** + +def isPandigitalZero( n ): + n = getMPFIntegerAsString( n ) + + length = len( n ) + + if length < 10: + return 0 + + digitsToCheck = string.digits + + for c in digitsToCheck: + if c not in n: + return 0 + + return 1 + + +@oneArgFunctionEvaluator( ) +@argValidator( [ IntValidator( 0 ) ] ) +def isPandigitalZeroOperator( n ): + return isPandigitalZero( n ) + + #****************************************************************************** # # containsDigitsOperator diff --git a/rpn/rpnOperators.py b/rpn/rpnOperators.py index 1cc5b98..5279f32 100644 --- a/rpn/rpnOperators.py +++ b/rpn/rpnOperators.py @@ -137,15 +137,16 @@ getDigitsOperator, getErdosPersistenceOperator, getPersistenceOperator, getKPersistenceOperator, \ getLeftDigitsOperator, getLeftTruncationsOperator, getNonzeroDigitsOperator, getNthReversalAdditionOperator, \ getRightDigitsOperator, getRightTruncationsOperator, isAutomorphicOperator, isBaseKNarcissisticOperator, \ - isBaseKPandigitalOperator, isBaseKSmithNumberOperator, isBouncyOperator, isDecreasingOperator, \ - isDigitalPermutationOperator, isGeneralizedDudeneyNumberOperator, isHarshadNumberOperator, isIncreasingOperator, \ - isKaprekarNumberOperator, isKMorphicOperator, isNarcissisticOperator, isOrderKSmithNumberOperator, \ - isPalindromeOperator, isPandigitalOperator, isPerfectDigitalInvariantOperator, \ - isPerfectDigitToDigitInvariantOperator, isSmithNumberOperator, isStepNumberOperator, isSumProductNumberOperator, \ - isTrimorphicOperator, multiplyDigitsOperator, multiplyDigitPowersOperator, multiplyNonzeroDigitPowersOperator, \ - multiplyNonzeroDigitsOperator, permuteDigitsOperator, replaceDigitsOperator, reverseDigitsOperator, \ - rotateDigitsLeftOperator, rotateDigitsRightOperator, showErdosPersistenceOperator, showKPersistenceOperator, \ - showPersistenceOperator, sumDigitsOperator + isBaseKPandigitalOperator, isBaseKPandigitalZeroOperator, isBaseKSmithNumberOperator, isBouncyOperator, \ + isDecreasingOperator, isDigitalPermutationOperator, isGeneralizedDudeneyNumberOperator, isHarshadNumberOperator, \ + isIncreasingOperator, isKaprekarNumberOperator, isKMorphicOperator, isNarcissisticOperator, \ + isOrderKSmithNumberOperator, isPalindromeOperator, isPandigitalOperator, isPandigitalZeroOperator, \ + isPerfectDigitalInvariantOperator, isPerfectDigitToDigitInvariantOperator, isSmithNumberOperator, \ + isStepNumberOperator, isSumProductNumberOperator, isTrimorphicOperator, multiplyDigitsOperator, \ + multiplyDigitPowersOperator, multiplyNonzeroDigitPowersOperator, multiplyNonzeroDigitsOperator, \ + permuteDigitsOperator, replaceDigitsOperator, reverseDigitsOperator, rotateDigitsLeftOperator, \ + rotateDigitsRightOperator, showErdosPersistenceOperator, showKPersistenceOperator, showPersistenceOperator, \ + sumDigitsOperator from rpn.special.rpnList import \ alternateSignsOperator, alternateSigns2Operator, appendListsOperator, calculateAntiharmonicMeanOperator, \ @@ -2980,6 +2981,7 @@ def createSizedRangeOperator( a, b, c ): 'has_only_digits' : RPNOperator( containsOnlyDigitsOperator, 2 ), 'is_automorphic' : RPNOperator( isAutomorphicOperator, 1 ), 'is_base_k_pandigital' : RPNOperator( isBaseKPandigitalOperator, 2 ), + 'is_base_k_pandigital_zero' : RPNOperator( isBaseKPandigitalZeroOperator, 2 ), 'is_base_k_smith_number' : RPNOperator( isBaseKSmithNumberOperator, 2 ), 'is_bouncy' : RPNOperator( isBouncyOperator, 1 ), 'is_decreasing' : RPNOperator( isDecreasingOperator, 1 ), @@ -2994,6 +2996,7 @@ def createSizedRangeOperator( a, b, c ): 'is_narcissistic' : RPNOperator( isNarcissisticOperator, 1 ), 'is_order_k_smith_number' : RPNOperator( isOrderKSmithNumberOperator, 2 ), 'is_pandigital' : RPNOperator( isPandigitalOperator, 1 ), + 'is_pandigital_zero' : RPNOperator( isPandigitalZeroOperator, 1 ), 'is_pddi' : RPNOperator( isPerfectDigitToDigitInvariantOperator, 2 ), 'is_pdi' : RPNOperator( isPerfectDigitalInvariantOperator, 1 ), 'is_smith_number' : RPNOperator( isSmithNumberOperator, 1 ), diff --git a/rpn/test/testRPN.py b/rpn/test/testRPN.py index 245d7b1..dcd61a3 100644 --- a/rpn/test/testRPN.py +++ b/rpn/test/testRPN.py @@ -2971,11 +2971,20 @@ def runLexicographyOperatorTests( ): expectEqual( '1 100000 range lambda x is_narcissistic filter', '5188 oeis 100000 filter_max' ) # is_pandigital + expectResult( '384759621 is_pandigital', 1 ) + expectResult( '3847590621 is_pandigital', 1 ) + expectResult( '384750621 is_pandigital', 0 ) + expectResult( '11335577998866442200 is_pandigital', 1 ) + expectResult( '1234567890 is_pandigital', 1 ) + expectResult( '1234567880 is_pandigital', 0 ) + + # is_pandigital_zero expectResult( '3847596201 is_pandigital', 1 ) expectResult( '11335577998866442200 is_pandigital', 1 ) expectResult( '1234567890 is_pandigital', 1 ) expectResult( '1234567880 is_pandigital', 0 ) + # is_pddi testOperator( '1253 4 is_pddi' ) diff --git a/rpn/util/rpnAliases.py b/rpn/util/rpnAliases.py index b1965e8..6a1078d 100644 --- a/rpn/util/rpnAliases.py +++ b/rpn/util/rpnAliases.py @@ -796,6 +796,7 @@ def dumpAliasesOperator( ): 'range3' : 'sized_range', 'ratios2' : 'cumulative_ratios', 're' : 'real', + 'recurrence' : 'sequence', 'rev_add' : 'reversal_addition', 'rev_dig' : 'reverse_digits', 'rev_digits' : 'reverse_digits',