¿Cómo me las arreglaría para math.ceilque un número se asigne a la siguiente potencia más alta de 10?
# 0.04 -> 0.1
# 0.7 -> 1
# 1.1 -> 10
# 90 -> 100
# ...
Mi solución actual es un diccionario que verifica el rango del número de entrada, pero está codificado y preferiría una solución de una línea. ¿Tal vez me estoy perdiendo un simple truco matemático o una función numpy correspondiente aquí?

10arriba, esto necesitará algo con, por ejemplolog10.Respuestas:
Puedes usar
math.ceilconmath.log10para hacer esto:log10(n)te da la soluciónxque satisface10 ** x == n, por lo que si la redondeasxte da el exponente para la próxima potencia más alta de 10.Tenga en cuenta que para un valor
ndondexya es un entero, la "próxima potencia más alta de 10" serán:fuente
10 ** math.ceil(math.log10(1)) == 1, que no es "la próxima potencia más alta"Su problema está subespecificado, debe retroceder y hacer algunas preguntas.
En otra respuesta, se propuso tomar el logaritmo, luego redondear hacia arriba (función de techo), luego exponer.
Lamentablemente, esto sufre de errores de redondeo. En primer lugar, n se convierte de cualquier tipo de datos que tenga en un número de coma flotante de doble precisión, lo que potencialmente introduce errores de redondeo, luego el logaritmo se calcula y posiblemente introduce más errores de redondeo tanto en sus cálculos internos como en su resultado.
Como tal, no me llevó mucho tiempo encontrar un ejemplo en el que proporcionara un resultado incorrecto.
También es teóricamente posible que falle en la otra dirección, aunque esto parece ser mucho más difícil de provocar.
Entonces, para una solución robusta para flotadores e ints, debemos suponer que el valor de nuestro logaritmo es solo aproximado y, por lo tanto, debemos probar un par de posibilidades. Algo en la línea de
Creo que este código debería dar resultados correctos para todos los argumentos en un rango sensible de magnitudes del mundo real. Se romperá para números muy pequeños o muy grandes de tipos no enteros y de punto flotante debido a problemas al convertirlos en punto flotante. Los argumentos enteros de casos especiales de Python para la función log10 en un intento de evitar el desbordamiento, pero aún con un número entero suficientemente masivo, es posible forzar resultados incorrectos debido a errores de redondeo.
Para probar las dos implementaciones utilicé el siguiente programa de prueba.
Esto encuentra muchas fallas en la implementación ingenua, pero ninguna en la implementación mejorada.
fuente
roundlugar demath.ceil? Esto introducirá muchos casos innecesarios donder < nes cierto y, por lo tanto, debe realizar un trabajo adicional.Parece que quieres más bien la próxima potencia más baja de 10 ... Aquí hay una manera de usar matemáticas puras y sin registro, sino recurrencia.
fuente
¿Algo así quizás? Está justo en la parte superior de mi cabeza, pero funcionó cuando probé algunos números en la terminal.
fuente
¡Mira esto!
Este código se basa en el principal del poder de diez
len( str( int( float_number ) ) ).Hay 4 casos:
int( i ) > 1.Floatnúmero - convertido aint, a partir de entonces una cadena astr()partir de él, nos dará unastringcon lalengthque estamos buscando exactamente. Entonces, la primera parte, para la entradai > 1.0, es diez10en potencia de esta longitud.i > 1.0yi > 0.1<=> es10y1respectivamente.i < 0.1: Aquí, diez estarán en poder negativo. Para obtener el primer elemento distinto de cero después de la coma, he utilizado dicha construcción("%.100f" % i ).replace('.','').index( k ), donde k se ejecuta en[1:10]intervalos. A partir de entonces, tome el mínimo de la lista de resultados. Y disminuir en uno, es el primer cero, que se contará. Además, aquí pitón de normaindex()puede bloquearse, si no va a encontrar por lo menos uno de no-cero elemento de[1:10]intervalo, que es lo que al final debo "filtro" lista de ocurrencia:if str( j ) in "%.100f" % i. Además, para obtener una precisión más profunda,%.100fpuede tomarse diferente.fuente