Zmiana znaczenia znaku ampersand w ciągu SQL


143

Próbuję wysłać zapytanie do określonego wiersza według nazwy w mojej bazie danych sql i ma ampersand. Próbowałem ustawić znak ucieczki, a następnie uciec przed ampersandem, ale z jakiegoś powodu to nie działa i nie jestem pewien, na czym dokładnie polega mój problem.

Set escape '\'
    select * from V1144engine.T_nodes where node_id in(
    select node2_id from V1144engine.T_edges where node1_id in(
    select node2_id from V1144engine.T_edges where node1_id in(
    select node2_id from V1144engine.T_edges where node1_id = 
      (select node_id from V1144engine.T_nodes where node_name = 'Geometric Vectors \& Matrices')))
    and edge_type_id = 1)
    and node_type_id = 1
    and node_id in (
    select node2_id from V1144engine.T_edges where node1_id =
      (select node_id from V1144engine.T_nodes where node_name = 'Algebra II')
    and edge_type_id = 2);

Chociaż daje to podobne rozwiązanie tego pytania , problemy są postawione bardzo różnie. Mogą skończyć z tym samym rozwiązaniem, ale to nie znaczy, że pytania są takie same.


Myślę, że nie potrzebujesz cytatu wokół postaci ucieczki ('\')
— mcalex

29
set define offto najprostszy sposób na zrobienie tego.
— AnBisw

Odpowiedzi:


205

Zamiast

node_name = 'Geometric Vectors \& Matrices'

posługiwać się

node_name = 'Geometric Vectors ' || chr(38) || ' Matrices' 

38 to kod ascii dla znaku ampersand iw tej formie zostanie zinterpretowany jako ciąg, nic więcej. Spróbowałem i zadziałało.

Innym sposobem może być użycie LIKE i podkreślenia zamiast znaku „&”:

node_name LIKE 'Geometric Vectors _ Matrices' 

Szansa, że ​​znajdziesz też inny rekord, który różni się tylko tą jedną postacią, jest dość niska.


45
Zamiast tego, co nieintuicyjne chr(38), możesz to zrobićnode_name = 'Geometric Vectors &' || ' Matrices'
— Jay Sullivan,

1
Dla innych biednych zagubionych dusz podobni do siebie, trzeba pamiętać, że jest chr(38), nie char(38) .
— xdhmoore

Zauważ, że &w MySQL nie ma potrzeby zmiany znaku ucieczki. MySQL również nie ma tej funkcji CHR().
— asmaier

113

Escape jest ustawiony \domyślnie , więc nie musisz go ustawiać; ale jeśli tak, nie zawijaj tego w cudzysłów.

Ampersand jest znacznikiem zmiennej substytucyjnej SQL * Plus ; ale możesz to zmienić lub, co bardziej przydatne w twoim przypadku, całkowicie go wyłączyć, za pomocą:

set define off

Wtedy nie musisz w ogóle zawracać sobie głowy ucieczką od wartości.


2
Znak zmiany znaczenia jest \ domyślnie ustawiony na , ale parametr boolowski escapejest domyślnie ustawiony na WYŁ. Więc OP może nie potrzebować ustawiać znaku ucieczki, ale musi to przynajmniej SET ESCAPE ONzrobić, aby to zadziałało. Lub oczywiście skorzystaj z innych, lepszych rozwiązań.
— mathguy

46

Możesz użyć

set define off

Użycie tego nie zapyta o dane wejściowe


32

prosto z książki o podstawach Oracle sql

SET DEFINE OFF
select 'Coda & Sid' from dual;
SET DEFINE ON

jak można od tego uciec bez ustalania definicji.


2
Pomocne jest dodanie opcji SET DEFINE ON.
— KSev,

@Roman Bez zdefiniowania również możesz użyć: wybierz 'Coda' '&' 'Sid' z dual; (podwójne cudzysłowy)
— antcalvente

8

Aby uciec &, możesz spróbować następujących sposobów: -

  1. set scan off
  2. set define off
  3. set escape on następnie zamień &na/&
  4. wymienić &na&&

Jeden z nich powinien przynajmniej działać.

Dodatkowo, jeśli używasz programisty PL / SQL, na dole okna sql znajduje się ikona &, przejdź tam i wyłącz ją . Uwaga w starszej wersji tej opcji nie ma.

Upewnij się również, że set define off jest napisane na samym początku skryptu.


2

Działa to również:

select * from mde_product where cfn = 'A3D"&"R01'

definiujesz &jako literał przez umieszczenie "&"w ciągu znaków podwójnych qoutes .


1
Jeśli to zrobisz, podwójne cudzysłowy staną się częścią ciągu, na przykład:A3D"&"R01
— David Balažic

2
set escape on
... node_name = 'Geometric Vectors \& Matrices' ...

lub alternatywnie:

set define off
... node_name = 'Geometric Vectors & Matrices' ...

Pierwsza pozwala na użycie ukośnika odwrotnego do zmiany znaku &.

Drugi wyłącza się & „globalnie” (nie trzeba nigdzie dodawać ukośnika). Możesz go ponownie włączyć, gdy set define oni od tego wiersza znaki ampersand odzyskają swoje specjalne znaczenie, więc możesz je wyłączyć dla niektórych części skryptu, a nie dla innych.



0

Napisałem wyrażenie regularne, aby pomóc znaleźć i zamienić „&” w INSERT, mam nadzieję, że to komuś pomoże.

Sztuczka polegała na upewnieniu się, że „&” występuje z innym tekstem.

Odnaleźć “(\'[^\']*(?=\&))(\&)([^\']*\')”

Zastąpić “$1' || chr(38) || '$3”

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.