Estoy tratando de hacer algunas cosas en Angular 2 Alpha 28, y tengo un problema con los diccionarios y NgFor.
Tengo una interfaz en TypeScript que se ve así:
interface Dictionary {
[ index: string ]: string
}
En JavaScript, esto se traducirá en un objeto que con datos podría verse así:
myDict={'key1':'value1','key2':'value2'}
Quiero repetir esto y probé esto:
<div *ngFor="(#key, #value) of myDict">{{key}}:{{value}}</div>
Pero en vano, ninguno de los siguientes funcionó tampoco:
<div *ngFor="#value of myDict">{{value}}</div>
<div *ngFor="#value of myDict #key=index">{{key}}:{{value}}</div>
En todos los casos recibo errores como "token inesperado" o "No se puede encontrar el objeto de soporte de tubería 'iterableDiff'"
¿Que me estoy perdiendo aqui? ¿Ya no es posible? (La primera sintaxis funciona en Angular 1.x) o ¿es diferente la sintaxis para iterar sobre un objeto?
Respuestas:
Parece que no quieren admitir la sintaxis de ng1.
Según Miško Hevery ( referencia ):
Entonces, para iterar sobre su objeto, necesitará usar una "tubería". Actualmente no hay una tubería implementada que haga eso.
Como solución alternativa, aquí hay un pequeño ejemplo que itera sobre las claves:
Componente:
fuente
key
asnumber
yvalue
comostring
pero angular está arrojando un errorexpression has changed after it was checked
? ¿Por qué tan alguna idea?Angular 6.1.0+ Respuesta
Use el
keyvalue
tubo incorporado de esta manera:o así:
dónde
mySortingFunction
está en su.ts
archivo, por ejemplo:Stackblitz: https://stackblitz.com/edit/angular-iterate-key-value
No necesitará registrar esto en ningún módulo, ya que las tuberías angulares funcionan de fábrica en cualquier plantilla.
También funciona para Javascript-Maps .
fuente
implements PipeTransform
la definición de clase (ver angular.io/guide/pipes#custom-pipes )return Object.keys(dict).map(key => ({key, val: dict[key]}))
?intenta usar esta pipa
fuente
Además de la respuesta de @ obscur, aquí hay un ejemplo de cómo puede acceder tanto a @View
key
comovalue
a @View.Tubo:
Ver:
Entonces, si el objeto se viera así:
El resultado generado sería:
Nombre: Daario
Apellido: Naharis
Nombre: Victarion
Apellido: Greyjoy
Nombre: Quentyn
Apellido: Ball
fuente
<li *ngFor="let u of myObject | keyValueFilter">First Name: {{u.key}} <br> Last Name: {{u.value}}</li>
. +1 de mi partereturn { 'key' : key, 'value' : value[key] };
Actualizado: Angular ahora proporciona la tubería para recorrer el objeto json a través de
keyvalue
:DEMO DE TRABAJO , y para más detalles Leer
Anteriormente (para la versión anterior): hasta ahora la respuesta mejor / más corta que encontré es (Sin ningún filtro de tubería o función personalizada desde el lado del componente)
DEMO DE TRABAJO
fuente
let item of myDict | keyvalue
Esto resolvió mi problema.Agregando a la excelente respuesta de SimonHawesome . He creado una versión sucinta que utiliza algunas de las nuevas funciones de mecanografía. Me doy cuenta de que la versión de SimonHawesome es intencionalmente detallada para explicar los detalles subyacentes. También he agregado una verificación de salida anticipada para que la tubería funcione para valores falsos . Por ejemplo, si el mapa es
null
.Tenga en cuenta que el uso de una transformación de iterador (como se hace aquí) puede ser más eficiente ya que no necesitamos asignar memoria para una matriz temporal (como se hizo en algunas de las otras respuestas).
fuente
PipeTransform
Aquí hay una variación de algunas de las respuestas anteriores que admite múltiples transformaciones (keyval, key, value):
Uso
fuente
pure: false
Es realmente importante para reflexiones instantáneas.Tuve un problema similar, construí algo para objetos y mapas.
fuente
implements PipeTransform
a la definición de claseAngular 2.x && Angular 4.x no admite esto fuera de la caja
Puede usar estos dos tubos para iterar por clave o por valor .
Tubo de llaves:
Tubería de valores:
Cómo utilizar:
fuente
Si alguien se pregunta cómo trabajar con objetos multidimensionales, aquí está la solución.
supongamos que tenemos el siguiente objeto en servicio
en componente agregar siguiente función
finalmente a la vista hacer lo siguiente
fuente
Me he estado arrancando el pelo al tratar de analizar y usar los datos devueltos de una consulta JSON / llamada de API. No estoy seguro exactamente de dónde estaba yendo mal, siento que he estado circulando la respuesta durante días, persiguiendo varios códigos de error como:
"No se puede encontrar el objeto de soporte de tubería 'iterableDiff'"
"La matriz de tipos genérica requiere uno o más argumentos"
Errores de análisis JSON, y estoy seguro de que otros
Supongo que acabo de tener la combinación incorrecta de correcciones.
Así que aquí hay un resumen de las trampas y cosas que debe buscar.
Primero verifique el resultado de sus llamadas a la API, sus resultados pueden ser en forma de un objeto, una matriz o una matriz de objetos.
No voy a profundizar demasiado, basta con decir que el error original del OP de no ser iterable generalmente es causado por tratar de iterar un objeto, no una matriz.
He aquí algunos de mis resultados de depuración que muestran variables de matrices y objetos.
Entonces, como generalmente nos gustaría iterar sobre nuestro resultado JSON, debemos asegurarnos de que tenga la forma de una matriz. Intenté numerosos ejemplos, y tal vez sabiendo lo que sé ahora, algunos de ellos funcionarían, pero el enfoque que utilicé fue implementar una tubería y el código que utilicé fue el publicado por t.888
Honestamente, creo que una de las cosas que me atrapó fue la falta de manejo de errores, al agregar la llamada 'devolver indefinido' creo que ahora estamos permitiendo que se envíen datos no esperados a la tubería, lo que obviamente estaba ocurriendo en mi caso .
si no desea lidiar con el argumento de la tubería (y mira, no creo que sea necesario en la mayoría de los casos) puede devolver lo siguiente
Algunas notas sobre cómo crear su tubería y página o componente que usa esa tubería
es que estaba recibiendo errores sobre 'nombre_de_mi_pipe' no encontrado
Use el comando 'iónico generar tubería' de la CLI para asegurarse de que los módulos de tubería.ts se creen y hagan referencia correctamente. asegúrese de agregar lo siguiente a la página mypage.module.ts.
(no estoy seguro si esto cambia si también tiene su propio custom_module, es posible que también deba agregarlo a custommodule.module.ts)
si usó el comando 'generar página iónica' para crear su página, pero decide usar esa página como su página principal, recuerde eliminar la referencia de la página de app.module.ts (aquí hay otra respuesta que publiqué sobre ese https: / /forum.ionicframework.com/t/solved-pipe-not-found-in-custom-component/95179/13?u=dreaser
En mi búsqueda de respuestas, hubo varias formas de mostrar los datos en el archivo html, y no entiendo lo suficiente como para explicar las diferencias. Puede que le resulte mejor usar uno sobre otro en ciertos escenarios.
Sin embargo, lo que funcionó que me permitió mostrar tanto el valor como la clave fue lo siguiente:
para hacer que la llamada a la API parezca que necesita importar HttpModule en app.module.ts
y necesita Http en la página desde la que realiza la llamada
Al hacer la llamada API, parece que puede acceder a los datos secundarios (los objetos o matrices dentro de la matriz) 2 formas diferentes, o parece funcionar
ya sea durante la llamada
o cuando asigna los datos a su variable local
(no estoy seguro si esa variable necesita ser una Cadena de matriz, pero eso es lo que tengo ahora. Puede funcionar como una variable más genérica)
Y nota final, no era necesario usar la biblioteca JSON incorporada, sin embargo, puede encontrar estas 2 llamadas útiles para convertir de un objeto a una cadena y viceversa.
Espero que esta compilación de información ayude a alguien.
fuente
fuente
Las interfaces en TypeScript son una construcción de tiempo de desarrollo (solo para herramientas ... 0 impacto en tiempo de ejecución). Debe escribir el mismo TypeScript que su JavaScript.
fuente
El diccionario es un objeto, no una matriz. Creo que ng-repeat requiere una matriz en Angular 2.
La solución más simple sería crear una tubería / filtro que convierta el objeto en una matriz sobre la marcha. Dicho esto, probablemente quieras usar una matriz como dice @basarat.
fuente
Si tiene
es6-shim
o sutsconfig.json
objetivoes6
, puede usar ES6 Map para hacerlo.fuente
Definir
MapValuesPipe
e implementar PipeTransform :Agregue su tubería en su módulo de tuberías. Esto es importante si necesita usar la misma tubería en más de un componente :
Luego, simplemente use la tubería en su html con
*ngFor
:<tr *ngFor="let attribute of mMap | mapValuesPipe">
Recuerde, deberá declarar su PipesModule en el componente donde desea usar la tubería:
fuente
Entonces, iba a implementar mi propia función auxiliar, objLength (obj), que devuelve solo Object (obj) .keys.length. Pero luego, cuando lo estaba agregando a mi plantilla * ngIf, mi IDE sugirió objectKeys (). Lo intenté y funcionó. Siguiendo con su declaración, parece ser ofrecido por lib.es5.d.ts, ¡así que ahí lo tienes!
Así es como lo implementé (tengo un objeto personalizado que usa claves generadas del lado del servidor como índice para los archivos que he cargado):
fuente