2012-04-19 7 views
10

Usando CakePHP 2.0 aquí. El título es un poco engañoso, así que para aclarar las cosas, tengo una matriz de sesión que se llena con los identificadores de los productos a medida que el usuario los agrega al carrito. Entonces esta matriz va como [0] => 25, [1] => 70 etc. Digamos que esta matriz se llama $ products.Cómo ordenar una matriz conservando su estado inicial

Lo que quiero preguntar es si hay alguna posibilidad de que la matriz se obtenga utilizando la función 'find' del modelo ('condiciones' => matriz ('Product.id' => $ products)) para ordenar por algunos valores de Model.field (como en la opción 'order'), pero por $ products array indices, de modo que cuando visualice el contenido de los productos, obtendría todos esos productos en el carrito ordenados en la secuencia en que el usuario los estaba agregando .

He aquí un ejemplo - Sesión array $ productos:

[0] => 35, 
[1] => 15, 
[2] => 25 

Luego paso esta matriz a las condiciones de función de búsqueda:

$list = $this->Product->find('all', array('conditions' => array('Product.id' => $products))); 

En la lista final $ me da gama, que ordenadas según ID del Producto. Así que en lugar de tener:

[0] => Array 
    (
     [Product] => Array 
      (
       [id] => 35)), 
[1] => Array 
     (
      [Product] => Array 
       (
        [id] => 15)), 

[2] => Array 
     (
      [Product] => Array 
       (
        [id] => 25)) 

me sale:

[0] => Array 
    (
     [Product] => Array 
      (
       [id] => 15)), 
[1] => Array 
     (
      [Product] => Array 
       (
        [id] => 25)), 
[2] => Array 
     (
      [Product] => Array 
       (
        [id] => 35)) 

Hasta ahora todas las respuestas no resuelve mi problema. Por favor, presten más atención al ejemplo que di, es muy simple, pero las respuestas proporcionadas son en clave diferente.

Una vez más, necesito gama lista definitiva $ que ser resuelto por los índices de matriz sesión $ productos, pero me da lista $ ordenados por el campo Product.id, a pesar de que no se hayan indicado ningún 'find(array('order'=> ...))' en absoluto e incluso trató de establecerlo en falso.

+3

no puede entender la pregunta, pero supongo que esto puede ayudar ... no se puede ordenar una matriz conservando su estado inicial (porque lo ordenó), pero podría almacenarlo dos veces o incluso mejor, podría almacenar almacenar los índices de la matriz en su estado inicial, para que pueda ordenar la matriz como lo hizo en su estado inicial (o viceversa) siempre que lo desee. $ initial_state_indexes = array_keys ($ the_array); –

+0

De acuerdo, la pregunta es un poco vaga ... Trate de aclarar su punto con el código o llegar desde un ángulo diferente – mseancole

+0

No estoy usando 'orden' en absoluto.Como dije, session array $ products contiene ids de productos en los que los índices (de [0] y así sucesivamente) representan la secuencia de productos añadidos por el usuario. –

Respuesta

2

No quiero sonar grosero, pero todas las respuestas a mi pregunta fueron sobre cómo ordenar mi matriz por Identificación de producto (que claramente no era lo que pregunté) o sugerencias sobre hacer consultas SQL manuales que no son apropiadas. Parece que no pude describir correctamente lo que necesitaba, pero traté de hacerlo lo más claro posible, lo siento.

Me encontré con una solución al tratar de encontrar la forma de 'desactivar el orden' en el pastel. Básicamente, lo que necesita hacer es tener una matriz (llamémoslo $ queue) donde guarda los identificadores del producto a medida que se agregan al carro, y luego en la opción 'ordenar' en encontrar la función del modelo (o paginación) que debería proporcionarlo como:

'order'=>array('FIELD(Product.id,'.implode(',', $queue).')') 

$ cola de podría tener este aspecto, como ejemplo:

[queue] => Array 
     (
      [0] => 51 
      [1] => 1 
      [2] => 11 
     ) 

al final se obtiene lista $ matriz en la que el orden de los productos es el mismo que en $ queue. Si no se ha especificado 'orden', entonces sería conseguir que lista $ gama de esta manera:

[queue] => Array 
      (
       [0] => 1 
       [1] => 11 
       [2] => 51 
      ) 
0

No puedo pensar en una simple consulta SQL que ordene los resultados según una lista de parámetros.

Así que lo más simple es probablemente reordenar los registros después de haberlos obtenido de la base de datos.

$records = $this->Product->find('all', array('conditions' => array('Product.id' => $products))); 

$sorted_records = array(); 
foreach($records as $record) 
{ 
    $key = array_search($record['Product']['id'], $products); 
    $sorted_records[$key] = $record; 
} 

ksort($sorted_records); 

debug($sorted_records); 
0

Ésta es SQL válida, no está seguro de cómo hacer cakephp la hacen, pero creo que va a resolver su problema de pedido:

SELECT * FROM product WHERE id IN (35, 15, 25) ORDER BY id = 35 DESC, id = 15 DESC, id = 25

0

Si he entendido bien lo que necesita para ordenar el resultado modelo , o en otras palabras establecer un orden en la consulta para ordenar de una manera arbitraria.

Aquí hay dos opciones:

  1. especificar un tipo. No está familiarizado con Cake pero el mysql que necesita generar es: order by id = 25 desc, id = 70 desc, id = etc (supongo que sería mejor probar order => 'id = 25 desc, id = 70 desc, id = etc') que debería ensamblar desde la matriz $products.

  2. cree un modelo de cesta y utilice una consulta de combinación para obtener la lista de productos en el orden correcto (no simple, pero probablemente sea mejor que contar con una var de sesión).

actualización

me había prestado atención y se soluciona el problema que le proporciona el SQL que necesitaba para generar, junto con una pista sobre la sintaxis de la torta. En cuanto a su solución publicada, su FIELD (id, x, x, x) está haciendo lo mismo, pero es una solución mucho más limpia. Bien hecho para encontrarlo, eliminaría sus comentarios de "no quiero ser grosero", ya que generalmente parecen poco grosero.

0

No estoy familiarizado con Cake o sus capas de bases de datos, pero tal vez pueda agregar un poco de sql.

El SQL relevante sería algo así como

order by field(myTable.myID, 35, 15, 25) 
-- or alternatively, more cross database compatible 
order by case when myTable.myID = 35 then 1 
       when myTable.myID = 15 then 2 
       when myTable.myID = 25 then 3 
     end 

sin embargo, el enfoque más universal sería simplemente cambiar el orden en el código php.

$products = array(35,15,25);//the ordered array 
$records = array_flip($products); 
foreach ($list as $row) { 
    $id = $row['Product']['id']; 
    $records[$id] = $row; 
} 
print_r($records); 
0

La forma en que suelen manejar este tipo de problemas es mediante la indexación de la lista $ por el identificador de producto utilizando la clase Set, que está integrado en la torta. Así

$list = Set::combine($list, '{n}.Product.id', '{n}.Product'); 

A continuación, utilice bucle a través de su compra ($ productos), que ya está en el orden que desee

foreach($products as $prod) echo $list[$prod]['Product']['name']; 

Espero que esto ayude.

Cuestiones relacionadas