2016-02-02 3 views
1

Я пытался перечислить все Yelp пользователей, которые не просмотрели ни бизнеса, но предоставили по крайней мере, 2 комментариев по отзывам других пользователей в следующей таблице: enter image description hereПроблемы SQL-запроса с подсчетом частоты

enter image description here

Но у меня были некоторые проблемы. Эти проблемы в основном проистекают из моих попыток подсчета элементов, перечисленных как varchar. Например, в вопросах указано, что мне нужно вернуть пользователей, которые прокомментировали по меньшей мере два отзыва других пользователей. В настоящее время у меня есть List_Of_Comments, хранящийся в виде varchar с символами, похожими на следующие: «Y3, Y2». Как я должен определить, как часто пользователь отправляет комментарий через VARCHAR Это то, что я до сих пор:

SELECT U.YELP_ID FROM REVIEWS R, YELP_USER U 
WHERE R.Author = U.YELP_ID AND R.Author = NULL AND R.Number_Of_Comments >= 2; 

Предполагая следующие таблицы:

CREATE TABLE REVIEWS (
REVIEW_ID VARCHAR(3), 
Stars INT, 
Author VARCHAR(3), 
Publish_Date VARCHAR(22), 
BUSSINESS_ID VARCHAR(3), 
List_Of_Comments VARCHAR(7), 
Number_Of_Comments INT 
); 

CREATE TABLE YELP_USER (
YELP_ID VARCHAR(3), 
Email VARCHAR(17), 
First_Name VARCHAR(8), 
Last_Name VARCHAR(17), 
DOB DATE, 
BirthPlace VARCHAR(3), 
Gender VARCHAR(1), 
Friendlist VARCHAR(9), 
Complimented_Friendlist VARCHAR(6), 
Checkedin_Businesses VARCHAR(36) 
); 

Если кто-то может помочь мне фигура это я был бы очень признателен. Я застрял на этом часами. Благодаря!

+2

так ... mysql, SQL Server или Oracle? – Lamak

+1

Ваша структура данных очень хлопотная. Кажется, что в некоторых столбцах вы разделили значения. Это нарушает 1NF и представляет собой серьезную боль, с которой приходится иметь дело. Разумеется, размеры этих столбцов препятствуют размещению любого реального количества информации в любом случае. –

+0

Извините, это Oracle SQL – John123

ответ

1

Для того, чтобы ответить на то, что я думаю, что вы просите ... Как подсчитать количество записей в разделенных запятыми:

Oracle Setup:

INSERT INTO REVIEWS VALUES (1, 1, 'A1', DATE '2016-02-02', 'B1', 'C1,C2', NULL); 
INSERT INTO REVIEWS VALUES (2, 1, 'A2', DATE '2016-02-01', 'B1', 'C3', NULL); 
INSERT INTO REVIEWS VALUES (3, 1, 'A3', DATE '2016-02-01', 'B1', NULL, NULL); 

Запрос:

SELECT REVIEW_ID, 
     COALESCE(REGEXP_COUNT(List_of_comments, '[^,]+'), 0) AS Number_of_comments 
FROM REVIEWS; 

Результаты:

REVIEW_ID NUMBER_OF_COMMENTS 
--------- ------------------ 
1       2 
2       1 
3       0 

Лучшее решение:

Сохранение его, как вы делаете с VARCHAR2(7) колонки для списка комментариев только позволит вам хранить, в лучшем случае, 4 Идентификаторы комментарий (если каждый идентификатор один символ).

Было бы лучше, чтобы переместить их в свои собственные таблицы, используя что-то вроде:

CREATE TABLE REVIEW_COMMENTS (
    COMMENT_ID NUMBER(8,0) PRIMARY KEY, 
    REVIEW_ID  VARCHAR2(3) REFERENCES REVIEWS(REVIEW_ID), 
    YELP_ID  VARCHAR2(3) REFERENCES YELP_USER(YELP_ID), 
    COMMENT_VALUE VARCHAR2(140) 
); 

COMMENT ON TABLE REVIEW_COMMENTS IS 'The comments on a review by a user.'; 
COMMENT ON COLUMN REVIEW_COMMENTS(COMMENT_ID) IS 'A unique identifier for the comment by a user on a review.'; 
COMMENT ON COLUMN REVIEW_COMMENTS(REVIEW_ID) IS 'The identifier for the review the comment was left against.'; 
COMMENT ON COLUMN REVIEW_COMMENTS(YELP_ID) IS 'The identifier for the user who left the comment.'; 
COMMENT ON COLUMN REVIEW_COMMENTS(COMMENT_VALUE) IS 'The text of the comment.'; 

Кроме того, не хранить даты в VARCHAR2 колонке.

0

Ваша структура данных допускает только 2 комментария для каждого обзора (по крайней мере, 2 символа для каждого обзора плюс две запятые). Любой другой комментарий не поместится в 7 символов), но, предполагая, что это то, что вы хотите, вы могли бы попытаться получить все пользователи, которых нет в поле обзора

... from yelp_users yu 
where not exists in (select 1 from reviews r where r.author = yu.yelp_id) 

и его идентификатор находятся в списке комментариев. Я хотел бы найти его с помощью инстр:

and exists (
    select 1 
    from reviews r 
    where instr(',' || r.list_of_comments || ',', ',' || yu.yelp_id || ',' , 1, 1) > 0) 

Я сцепляются «» чтобы избежать вам случай, когда вы смотрите на Y1 и в конечном итоге получить ложный положительный результат, когда Y11 является тот, который комментировал.

Как вы хотите, чтобы пользователи, которые прокомментировали, по крайней мере, дважды, вы можете перенести таблицу обзора из и поместить весь SQL в подзапрос, группируя идентификатор пользователя во внешнем SQL. =)

Смежные вопросы