Pergunta

Eu sinto que esta questão tem sido, provavelmente, pediu mil vezes já, por isso peço desculpas se ele foi respondido. E se assim for, alguém pode me aponte para os cargos certos / links?

O que estou tentando fazer é construir uma navegação facetada para o meu site. Ele usa MySQL e aqui está um esboço das mesas que estou usando:

products:
- id
- title
- description
attributes:
- product_id
- name
- value
categories:
- id
- name
products_to_categories:
- product_id
- category_id

O que eu quero fazer é exibir uma lista de atributos disponíveis quando você está em uma categoria, permitindo que você selecione um ou mais valores para cada um desses atributos. Para lhe dar um exemplo, olhe para esta página de Office Depot: http : //www.officedepot.com/a/browse/binders/N=5+2177/

Até agora eu usei um monte de junta para filtrar em vários atributos:

SELECT products.*, a_options.*
FROM products_to_categories AS pc, products,
attributes AS a_options,    /* list of attribute/value pairs I can continue to refine on */
attributes AS a_select1     /* first selected attribute */
attributes AS a_select2     /* second selected attribute */
...
WHERE pc.category_id = 1
AND products.id = pc.product_id
AND a_options.product_id = products.id
AND a_options.name != 'Color' AND a_options.name != 'Size'
AND a_select1.product_id = products.id
AND a_select1.name = 'Color' AND (a_select1.value = 'Blue' OR a_select1.value = 'Black')
AND a_select2.product_id = products.id
AND a_select2.name = 'Size' AND a_select2.value = '8.5 x 11'

Basicamente a_options retornará todos os atributos para os produtos que são um subconjunto dos filtros eu aplicadas usando a_select1 e a_select2. Então, se eu usar o exemplo Binders de Office Depot, eu quero mostrar todos os atributos disponíveis após a seleção azul ou preta para Color e "8,5 x 11" para o tamanho.

Eu, então, usar o código PHP para remover duplicatas e organizar os atributos resultantes em uma matriz como este:

attributes[name1] = (val1, val2, val3, ...)
attributes[name2] = (val1, val2, val3, ...)

Existe uma maneira que eu posso acelerar o meu consulta ou escrevê-lo de forma mais eficiente? Tenho índices de configuração no nome e valor na tabela de atributos (e também sobre todos os números de ID). Mas se alguém selecionar um par de atributos, em seguida, a consulta é executada lento.

Obrigado por sua ajuda com antecedência,
Sridhar

Foi útil?

Solução

"Eu, então, usar o código PHP para remover duplicatas"

Não será ampliado em seguida.

Depois que eu li http://www.amazon.com/Data-Warehouse-Toolkit -Técnicas-dimensional / dp / 0471153370 eu estava desenrolando facetas & filtragem mecanismos non stop.

A idéia básica é utilizar um esquema em estrela ..

Você cria uma tabela de fatos que armazena fatos

customerid | dateregisteredid | datelastloginid
1 | 1 | 1
2 | 1 | 2

Você usa chaves estrangeiras em tabelas de dimensão que atributos loja

date_registered
Id | weekday | weeknumber | year | month | month_year | daymonth | daymonthyear
1 | Wed      | 2            | 2009 | 2   |2-2009      | 4        | 4-2-2009

Então whichver data "paradigma" que você está usando, pegue todos os ids de que a tabela dimensão e

 select * from the fact table where the fact.dateregisteredid is IN( ... the ids from the date dimension table that represent your time period)

Esses "pontos de vista indexados" de seus dados devem residir em um banco de dados separado, e uma alteração em um objeto na produção deve fila que recorde para re-indexação no sistema de análise. Grande lote sites podem seus registros em horários fora do pico para as estatísticas de relatórios de aplicação sempre fica para trás algumas horas ou dias. Eu sempre tento mantê-lo até o segundo, se a arquitetura suporta.

Se você está exibindo previews rowCount, você pode ter algum optimization ou Cache para implementar também.

Basicamente, para resumir, você copiar dados e denormalize. A técnica atende pelo nome de "armazenamento de dados" ou OLAP (análise online processamento).

Existem melhores formas, utilizando bases de dados comerciais como o Oracle, mas o esquema em estrela torna disponível para qualquer pessoa com um banco de dados relacional de código aberto e algum tempo.

Você deve definitivamente ler o kit de ferramentas, mas ele discute um monte de coisas que você pode economizar tempo considerável. Como estratégias para lidar com dados atualizados, e retenção de histórico de auditoria na aplicação de relatórios. Para cada problema que ele apresenta várias soluções, cada uma das quais são aplicáveis ??em diferentes contextos.

Ele pode escalar até milhões de linhas, se você não tomar as maneiras fáceis e usar uma tonelada de desnecessária junta.

Outras dicas

Você pode gerar uma tabela faceta baseado em suas tabelas de banco de dados normalizado.
Por exemplo:

> SELECT * FROM product_facet
product_id | facet_type | facet_value
1          | color      | blue
2          | color      | blue
3          | color      | green
4          | color      | yellow
1          | speed      | slow
2          | speed      | slow

Em seguida, basta fazer esta consulta para obter total por atributo:

SELECT facet_type, facet_value, COUNT(facet_value) as total
FROM product_facet
GROUP BY facet_type, facet_value;

Resultado:

facet_type | facet_value | total
color      | blue        | 2
color      | green       | 1
color      | yellow      | 1
speed      | slow        | 2

Ao procurar com critérios, você pode selecionar a tabela a faceta de identificação do produto jogo:

SELECT facet_type, facet_value, COUNT(facet_value) as total
FROM product_facet
WHERE product_id in (SELECT product_id FROM products WHERE ... )
GROUP BY facet_type, facet_value;
Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top