Есть ли опечатка, или return C;
действительно перед звонками на free
? Я не уверен, как компилятор позволяет это, не генерируя хотя бы предупреждение. Как написано, код для освобождения объектов, который находится после оператора return, никогда не будет выполняться.
Это:
C=0;for(i=0;i<7;i++){C+=sqr(beta[i]-BETA[i]);}C+=sqr(var-BETA[7]);
return C;
for(i=0;i<size_i*size_time*size_sim;++i){free(DATA_SIM[i]);free(X[i]);}free(DATA_SIM);free(X);
free(par); free(beta);free(Y);free(epsilon);
Вы можете сделать это довольно легко с помощью (введено в PostgreSQL 8.2) VALUES (), ().
Синтаксис будет таким:
select c.*
from comments c
join (
values
(1,1),
(3,2),
(2,3),
(4,4)
) as x (id, ordering) on c.id = x.id
order by x.ordering
Я согласен со всеми другими плакатами, в которых говорится «не делайте этого» или «SQL не хорош в этом». Если вы хотите выполнить сортировку по какому-либо аспекту комментариев, добавьте еще один целочисленный столбец в одну из ваших таблиц, чтобы содержать критерии сортировки и сортировать по этому значению. например, "ORDER BY comments.sort DESC" Если вы хотите сортировать их каждый раз в другом порядке, тогда ... SQL в этом случае вам не подойдет.
create sequence serial start 1;
select * from comments c
join (select unnest(ARRAY[1,3,2,4]) as id, nextval('serial') as id_sorter) x
on x.id = c.id
order by x.id_sorter;
drop sequence serial;
[EDIT]
unnest еще не встроен в 8.3, но вы можете создать его самостоятельно (красота любого *):
create function unnest(anyarray) returns setof anyelement
language sql as
$$
select $1[i] from generate_series(array_lower($1,1),array_upper($1,1)) i;
$$;
эта функция может работать с любым типом:
select unnest(array['John','Paul','George','Ringo']) as beatle
select unnest(array[1,3,2,4]) as id
А вот еще одно решение, которое работает и использует постоянную таблицу ( http://www.postgresql.org/docs/8.3/interactive /sql-values.html):
SELECT * FROM comments AS c,
(VALUES (1,1),(3,2),(2,3),(4,4) ) AS t (ord_id,ord)
WHERE (c.id IN (1,3,2,4)) AND (c.id = t.ord_id)
ORDER BY ord
Но опять же, я не уверен, что это работает.
Теперь у меня есть несколько ответов.
без ПОСЛЕДОВАТЕЛЬНОСТИ, работает только на 8.4:
select * from comments c
join
(
select id, row_number() over() as id_sorter
from (select unnest(ARRAY[1,3,2,4]) as id) as y
) x on x.id = c.id
order by x.id_sorter
SELECT * FROM "comments" JOIN (
SELECT 1 as "id",1 as "order" UNION ALL
SELECT 3,2 UNION ALL SELECT 2,3 UNION ALL SELECT 4,4
) j ON "comments"."id" = j."id" ORDER BY j.ORDER
или, если вы предпочитаете зло добру:
SELECT * FROM "comments" WHERE ("comments"."id" IN (1,3,2,4))
ORDER BY POSITION(','+"comments"."id"+',' IN ',1,3,2,4,')
Изучив это еще раз, я нашел следующее решение:
SELECT * FROM "comments" WHERE ("comments"."id" IN (1,3,2,4))
ORDER BY CASE "comments"."id"
WHEN 1 THEN 1
WHEN 3 THEN 2
WHEN 2 THEN 3
WHEN 4 THEN 4
END
Однако это кажется довольно многословным и может иметь проблемы с производительностью с большими наборами данных. Кто-нибудь может прокомментировать эти вопросы?
Для этого, я думаю, вам, вероятно, следует иметь дополнительную таблицу «ORDER», которая определяет сопоставление идентификаторов для заказа (эффективно выполняя то, что сказано в вашем ответе на ваш собственный вопрос), которую вы можете затем используйте в качестве дополнительного столбца в выбранном вами столбце, по которому затем можно выполнить сортировку.
Таким образом, вы явно описываете желаемый порядок в базе данных, где он должен быть.
Небольшое улучшение по сравнению с версией, в которой используется последовательность, я думаю:
CREATE OR REPLACE FUNCTION in_sort(anyarray, out id anyelement, out ordinal int)
LANGUAGE SQL AS
$$
SELECT $1[i], i FROM generate_series(array_lower($1,1),array_upper($1,1)) i;
$$;
SELECT
*
FROM
comments c
INNER JOIN (SELECT * FROM in_sort(ARRAY[1,3,2,4])) AS in_sort
USING (id)
ORDER BY in_sort.ordinal;