Pessoal estou com um probleminha. Tenho uma tabela com dados sobre MW (massa molecular) e PI de umas proteínas, preciso contar quantas proteínas estão em determinados intervalos, como pI entre 3 e 3,99, 4 e 4,99, sucessivamente até 10, e dentro dessa classificação contar os que tem mw menor que 20000, entre 20000 e 40000, e sucessivamente até maior que 80000. O resultado seria uma tabela como mostrada abaixo:
Já encontrei algumas coisas mas não deu certo, queria ajuda de vocês.
Como está a estrutura das suas tabelas?
Sem isso fico difícil ajudar.
O que foi que já encontrou?
Só utilizo uma tabela, esta possui o id da proteína o PI e a MW.
Eu encontrei um código que quase resolve meu problema, mas ainda não deu certo, acabei esquecendo de colocar.
select case when "MW" < 20000 then
'1 - menor que 20'
when "MW" between 20000 and 39999 then
'2 - de 20 a 40'
when "MW" between 40000 and 59999 then
'3 - de 40 a 60'
when "MW" between 60000 and 80000 then
'4 - de 60 a 80'
when "MW" > 80000 then
'5 - maior que 80'
end as faixa
, count(*) as total
from proteinas.dados WHERE "pI" BETWEEN 3 AND 3.999
group by "faixa" order by "faixa";
Código apenas para PI entre 3 e 3,999, para os outros basta apenas mudar o final. Eu estava querendo buscar cada faixa de PI separadamente e ir colocando em uma outra tabela e no final ter a tabela que eu mostrei no começo, mas isso seria só quando eu resolver o problema desse código, pois ele me dá o que quero, só que quando não há proteínas no intervalo, ele não mostra 0, apenas não mostra nada, e eu preciso do 0.
Eis a tabela com os dados (as colunas são spotid, pi, mw)
dados.txt (5.2 KB)
Veja se isso te ajuda
-- entrada (mw_minimo, mw_maximo, mw_faixa, pi_minimo, pi_maximo, pi_faixa)
create or replace function calcula(integer, integer, integer, integer, integer, integer) returns text as $$
declare
mw integer;
pi integer;
valor integer;
output TEXT = '';
BEGIN
FOR mw IN
select i
from generate_series($1, $2, $3) g(i)
LOOP
FOR pi IN
select j
from generate_series($4, $5, $6) gs(j)
LOOP
select count(a.*) into valor
from teste.a a
where a.mw between mw and (mw + $3) and a.pi between pi and (pi + $6);
output = output || ' \t ' || valor;
END LOOP;
output = output || chr(10) || chr(13);
END LOOP;
return output;
END;
$$ language plpgsql;
select calcula(0, 100000, 20000, 3, 10, 1);
Muito bom seu código! Porém, aqui não reconheceu o ‘\t’ nem o chr( ), mas de antemão já foi de grande ajuda! Vou ver se consigo arrumar essa última parte! Valeu mesmo!
Qual o banco que vc está usando?