Восклицательные знаки в SQL-запросе - PullRequest
13 голосов
/ 18 мая 2010

Я читаю по этому запросу и натолкнулся на строку, где я не понимаю, вот строка

[FETT List]![FETT Search]
  1. FETT List - таблица
  2. Поиск FETT - это столбец в списке FETT

Может кто-нибудь объяснить, что означает восклицательный знак?

Спасибо

Ответы [ 3 ]

18 голосов
/ 19 мая 2010

Ну, вы узнаете что-то новое каждый день!

Первоначально я планировал объяснить, что если бы вы сказали, что ссылка была [Forms]! [FETT List]! [FETT Search], то это было бы легко объяснить, как ссылку на элемент управления [FETT Search] в форме [FETT List]. Но без родительской коллекции (либо отчетов форм) она не выглядит как допустимая ссылка ни в одном контексте в инструкции SQL.

Но затем я подумал проверить его и обнаружил (к моему удивлению), что этот оператор SQL рассматривается как действительный в форме доступа:

  SELECT [tblCustomer]![LastName] AS LastName 
  FROM tblCustomer;

В Access это на 100% эквивалентно этому оператору SQL:

  SELECT tblCustomer.LastName 
  FROM tblCustomer;

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

Теперь длинный ответ на общий вопрос! (взрыв) против. (Точка):

Как правило, в Access оператор bang определяет коллекцию объекта и его элементов по умолчанию. Оператор точки определяет объект и его методы, свойства и элементы.

Это для Access и применяется к объектам Access и объектной модели для Access.

Но вы также используете SQL в Access, и поэтому у вас также есть TableName.FieldName в SQL, где оператор точки разделяет элемент в коллекции по умолчанию. TableName.FieldName может считаться сокращенным для TableName.Fields («FieldName»), поскольку вы обнаружите, что Forms! MyForm! MyControl эквивалентны Forms! MyForm.Controls («MyControl»). Но это правило не применяется в SQL - TableName.Fields ("FieldName") не является допустимым SQL, только TableName.FieldName.

Итак, вы должны четко указать, какая парадигма управляет пространством имен, в котором вы работаете, т. Е. Пространством имен Access или пространством имен SQL.

Forms! MyForm также эквивалентен Forms.Item («MyForm»), поэтому сверхдлинной формой будет Forms.Items («MyForm»). Controls («MyControl»). Обратите внимание, что оператор bang является ярлыком для более длинной версии формы с оператором точки, поэтому оператор bang довольно часто используется вместо оператора точки. Также обратите внимание, что более длинная форма в конечном итоге используется, когда вам нужно обратиться к элементу, имя которого хранится в переменной, что невозможно с помощью оператора bang:

  Dim strForm As String

  strForm = "MyForm"
  ' This is OK
  Debug.Print Forms(strForm).Controls.Count
  ' This is not
  Debug.Print Forms!strForm.Controls.Count

Кроме того, в коде VBA Microsoft разработала способы, чтобы скрыть это различие в формах и отчетах, где раньше было то, что Me! MyFavoriteControl был легален в качестве контрольной ссылки, а Me.MyFavoriteControl был бы легален только в качестве ссылки в пользовательское свойство (или переменную уровня модуля, которая будет членом объекта). Вы также можете неразумно назвать функцию или подпункт «MyFavoriteControl», и на него можно ссылаться с помощью оператора точки.

Но с появлением VBA MS представила неявно созданные (и поддерживаемые) оболочки скрытых свойств вокруг всех элементов управления, чтобы вы могли использовать оператор точки. Это имело одно огромное преимущество - проверка контрольных ссылок во время компиляции. То есть, если вы введете Me.MyFavoriteControl, и в этом пространстве имен формы или отчета не будет никакого элемента управления с этим именем и другого члена любого типа с таким именем, вы получите ошибку во время компиляции (действительно, вы будете сообщать об ошибке, как только вы вышли из строки кода, где вы сделали ошибку). Итак, если у вас был этот код:

  Debug.Print Me.Control1

... и вы переименовали Control1 в MyControl, в следующий раз вы получите сообщение об ошибке.

Что может быть обратной стороной проверки во время компиляции? Ну и несколько вещей:

  1. код становится все труднее понять программисту. В прошлом ссылка Me! Означала элемент в коллекции форм / отчетов по умолчанию (которая представляет собой объединение коллекций полей и элементов управления). Но Me.Reference может быть элементом управления или полем, или пользовательским свойством, или общедоступной переменной уровня модуля, или общедоступной подпрограммой / функцией, или, или, или ... Таким образом, он жертвует немедленной понятностью кода.

  2. вы зависите от неявного поведения VBA и его компиляции. Хотя обычно это нормально (особенно если вы хорошо заботитесь о своем коде), VBA-компиляция очень сложна и подвержена повреждению . На протяжении многих лет опытные разработчики сообщали, что использование оператора точки делает код более подверженным повреждению, поскольку он добавляет еще один слой скрытого кода, который может быть синхронизирован с частями приложения, которые вы можете явно изменить.

  3. , так как вы не можете управлять этими неявными оболочками свойств, когда они работают неправильно, вы должны воссоздать свой несущий модуль объект с нуля (обычно SaveAsText достаточно, чтобы очистить повреждение, не теряя ничего).

Итак, многие опытные разработчики (включая меня) не используют оператор точки для элементов управления в формах / отчетах.

Это не такая большая жертва, как некоторые могут подумать, если вы используете стандартный набор соглашений об именах. Например, со связанными элементами управления на формах, пусть они используют имена по умолчанию (то есть имя поля, с которым связан элемент управления). Если я не обращаюсь к элементу управления в коде, я никогда не изменяю его имя. Но в первый раз, когда я ссылаюсь на него в коде, я изменяю его имя так, чтобы имя элемента управления отличалось от имени поля, к которому оно привязано (это устранение неоднозначности имеет решающее значение в определенных контекстах). Итак, текстовое поле с именем MyField становится txtMyField, когда я решаю сослаться на него в коде. Единственный раз, когда я изменю имя поля после написания кода, это если я каким-то образом решил, что поле было названо неправильно. В этом случае достаточно просто найти / заменить.

Некоторые утверждают, что они не могут отказаться от Intellisense, но это неправда, что вы полностью отказываетесь от него, когда используете оператор bang. Да, вы отказываетесь от «действительно интеллектуального» Intellisense, то есть версии, которая ограничивает список Intellisense методами / свойствами / членами выбранного объекта, но мне это не нужно - мне нужен Intellisense для сохранения нажатий клавиш и с помощью Ctrl-SPACEBAR вы получаете полный список Intellisense, который автоматически заполняется точно так же, как и контекстно-зависимый Intellisense, и может затем замкнуть печать.

Другая область путаницы точка / взрыв связана с наборами записей DAO в коде VBA, в которых вы используете оператор точки для SQL, который вы используете для открытия набора записей, и оператор взрыва для ссылки на поля в результирующем наборе записей:

  Dim rs As DAO.Recordset

  Set rs = CurrentDB.OpenRecordset("SELECT MyTable.MyField FROM MyTable;")
  rs.MoveFirst
  Debug.Print rs!MyField

  rs.Close
  Set rs = Nothing

Если вы помните, в каком пространстве имен вы работаете, это не так смущает - точка используется в операторе SQL, а удар в коде DAO.

Итак, подведем итог:

  1. в SQL вы используете оператор точек для полей в таблицах.

  2. в формах и отчетах вы используете оператор взрыва для элементов управления и оператор точки для свойств / методов (хотя вы также можете использовать оператор точки, но это не обязательно рекомендуется).

  3. в коде VBA ссылки на элементы управления в формах и отчетах могут использовать либо точки, либо взрыва, хотя точка может быть склонна к возможному повреждению кода.

  4. в SQL вы можете увидеть используемый оператор взрыва, но только если в форме или отчете Access есть ссылка на элемент управления в форме «Form! FormName! ControlName» или «Report! ReportName! ControlName».

  5. в коде VBA, работающем с наборами записей DAO, вы можете увидеть операторы «точка» и «взрыв», первый при определении SQL, который используется для открытия набора записей, а второй - один раз для ссылки на поля в результирующем наборе записей. это открыто.

Это достаточно сложно для вас?

9 голосов
/ 18 мая 2010

Обычно вы видите это в коде MS Access (для восклицательного знака - точка для SQL-сервера). Вы можете ссылаться на столбец по table.column или, если вы дадите таблице псевдоним, то по alias.column. Вы можете сделать это, если вы хотите быть конкретным при использовании объединений, или вам может потребоваться сделать это, когда две (или более) таблицы в запросе / объединении имеют одинаковое имя столбца в каждой таблице.

0 голосов
/ 18 мая 2010

Я думаю, что восклицательный знак - это всего лишь обычный разделитель.

В Oracle PL / SQL вы используете точку:

[FETT List]. [FETT Search]

Любые другие подсказки?!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...