Actualización en 2018.10.31
Este error se solucionó en iOS 12.1, que tenga un buen día ~
Encontré un problema con el estado del valor de Array en el iOS 12 Safari recientemente lanzado, por ejemplo, un código como este:
<!DOCTYPE html> <html> <head> <meta charset="utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0"> <title>iOS 12 Safari bugs</title> <script type="text/javascript"> window.addEventListener("load", function () { let arr = [1, 2, 3, 4, 5]; alert(arr.join()); document.querySelector("button").addEventListener("click", function () { arr.reverse(); }); }); </script> </head> <body> <button>Array.reverse()</button> <p style="color:red;">test: click button and refresh page, code:</p> </body> </html>Después de actualizar la página, el valor de la matriz aún se invierte. ¿Es esto un error o una característica del nuevo Safari?
Aquí hay una página de demostración. Intenta usarlo con iOS 12 Safari: https://abelyao.github.io/others/ios12-safari-bug.html
¡Definitivamente es un ERROR! Y es un error muy grave.
El error se debe a la optimización de los inicializadores de matrices en los que todos los valores son literales primitivos. Por ejemplo, dada la función:
function buildArray() { return [1, null, 'x']; } Todas las referencias de matriz devueltas de las llamadas a buildArray() se vincularán a la misma memoria, y algunos métodos como toString() tendrán sus resultados almacenados en caché. Normalmente, para preservar la consistencia, cualquier operación mutable en dichas matrices optimizadas copiará los datos en un espacio de memoria separado y se vinculará a él; este patrón se llama copy-on-write o CoW para abreviar.
El método reverse() muta la matriz, por lo que debería activar una copia en escritura. Pero no es así, porque el implementador original (Keith Miller de Apple) se perdió el caso reverse() , a pesar de que había escrito muchos casos de prueba.
Este error se informó a Apple el 21 de agosto. La solución llegó al repositorio de WebKit el 27 de agosto y se envió en Safari 12.0.1 e iOS 12.1 el 30 de octubre de 2018.
Escribí una lib para corregir el error. https://www.npmjs.com/package/array-reverse-polyfill
(function() { function buggy() { var a = [1, 2]; return String(a) === String(a.reverse()); } if(!buggy()) return; var r = Array.prototype.reverse; Array.prototype.reverse = function reverse() { if (Array.isArray(this)) this.length = this.length; return r.call(this); } })();Este es un error en webkit . Aunque esto se resolvió al final, pero aún no se envió con el lanzamiento de iOS GM. Una de las soluciones a este problema:
(function() { function getReverseStr() { return [1, 2].reverse(); } var n1 = getReverseStr()[0]; var n2 = getReverseStr()[0]; // check if there is an issue if(n1 != n2) { var origReverseFunction = Array.prototype.reverse; Array.prototype.reverse = function() { var newArr = this.slice(); // use original reverse function so that edge cases are taken care of origReverseFunction.apply(newArr, arguments); var that = this; // copy reversed array newArr.forEach(function(value, index) { that[index] = value; }); return this; } } })();