문자열에 포함 된 경우 Postgresql SELECT


105

그래서 내 Postgresql에 있습니다.

TAG_TABLE
==========================
id            tag_name       
--------------------------
1             aaa
2             bbb
3             ccc

내 문제를 단순화하기 위해 문자열 "aaaaaaaa"에 'tag_name'이 포함 된 경우 TAG_TABLE에서 SELECT 'id'를 선택합니다. 따라서 이상적으로는 태그 이름 'aaa'의 ID 인 "1"만 반환해야합니다.

이것이 내가 지금까지하고있는 일입니다.

SELECT id FROM TAG_TABLE WHERE 'aaaaaaaaaaa' LIKE '%tag_name%'

그러나 postgres는 '% tag_name %'이 해당 열 아래의 실제 데이터 값 대신 하위 문자열 'tag_name'을 포함하는 패턴을 의미한다고 생각하기 때문에 이것은 작동하지 않습니다.

tag_name을 패턴에 어떻게 전달합니까 ??

답변:


131

따옴표 밖에 'tag_name'을 사용해야합니다. 그런 다음 레코드 필드로 해석됩니다. '||'를 사용하여 연결 문자 그대로 퍼센트 기호로 :

SELECT id FROM TAG_TABLE WHERE 'aaaaaaaa' LIKE '%' || tag_name || '%';

5
tag_name은 "; drop table TAG_TABLE; --"무엇일까요?
Denis de Bernardy 2014

24
@Denis : 아무 일도 일어나지 않습니다. WHERE절이로 평가 되기 때문에 행이 없습니다 FALSE. 이 명령문은 동적이 아니며 값만 연결되며 SQL 삽입이 불가능합니다.
Erwin Brandstetter 2014

1
aaaa와 tag_name의 순서가 반대로되어서는 안 되나요? 나는 당신이 어디에 열 이름을 넣어야한다는 것을 의미합니다
user151496

@ user151496 패턴이 LIKE키워드 의 오른쪽으로 이동해야하므로 아니요 .
jpmc26

4
LIKE패턴 에서 변수를 사용 하면 해당 변수에 밑줄 (_) 또는 퍼센트 문자 (%)가 포함 된 경우 의도하지 않은 결과가 발생할 수 있습니다. 예를 들어 다음 함수를 사용하여 이러한 문자를 이스케이프해야 할 수 있습니다. CREATE OR REPLACE FUNCTION quote_for_like(text) RETURNS text LANGUAGE SQL IMMUTABLE AS $$ SELECT regexp_replace($1, '([\%_])', '\\\1', 'g'); $$;(Freenode의 #postgresql IRC 채널에서 사용자 MatheusOl에서).
Martin von Wittich

46

개인적으로 ~ 연산자의 더 간단한 구문을 선호합니다.

SELECT id FROM TAG_TABLE WHERE 'aaaaaaaa' ~ tag_name;

차이점 을 이해하기 위해 Postgres에서 LIKE와 ~의 차이점을 읽을 가치 가 있습니다. `


2
이것은 tag_name적절한 REGEX 일 때만 작동합니다 . 꽤 위험합니다.
Jakub Fedyczak

@JakubFedyczak ***=postgresql.org/docs/current/static/functions-matching.html에 언급 된 사용할 수있는 리터럴 tag_name과 일치 합니다. 그러나 나는 strpos/ position솔루션에 비해 너무 느리다는 것을 발견했습니다 .
phunehehe

27

문자열을 검색하기위한 적절한 방법은 사용하는 것입니다 position대신 기능을 like탈출해야합니다 표현 %, _그리고 (이스케이프 문자 \기본값) :

SELECT id FROM TAG_TABLE WHERE position(tag_name in 'aaaaaaaaaaa')>0;

이것이 올바른 방법입니다. 아무도 해키 정규식 접근 방식을 사용해서는 안됩니다.
khol

LIKEILIKE사용할 수있는 gin인덱스를. position할 수 없습니다.
Eugene Pakhomov

14

용액과 더불어 'aaaaaaaa' LIKE '%' || tag_name || '%'있다 position(인수의 역순)와 strpos.

SELECT id FROM TAG_TABLE WHERE strpos('aaaaaaaa', tag_name) > 0

더 효율적인 것 외에도 (LIKE가 덜 효율적으로 보이지만 인덱스가 상황을 변경할 수 있음) LIKE에는 매우 사소한 문제가 있습니다. 물론 tag_name 에는 오탐을 제공하지 않기 위해 %특히 _(단일 문자 와일드 카드) 포함해서는 안됩니다 .


2
strpos는 항상 0을 반환했기 때문에 strpos를 위치로 바꿔야했습니다
jcf

-2
SELECT id FROM TAG_TABLE WHERE 'aaaaaaaa' LIKE '%' || "tag_name" || '%';

tag_name 따옴표 안에 있어야합니다. 그렇지 않으면 tag_name이 존재하지 않으므로 오류가 발생합니다.


2
이것은 받아 들여지는 대답 과 정확히 반대입니다 . 이 열 ... 할 필요가있는 동안 당신은 문자열로 합치하는
SURAJ 라오
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.