2017-01-11 11 views
0

Когда я использую инструкцию PROC SQL в SAS, иногда мне нужно преобразовать переменную из символа в числовой или наоборот. Я обычно использую следующие два запроса:Преобразование типов переменных из символа в числовое с неопределенной длиной в SAS

INPUT(A.KEY_ID, 8.) = B.KEY_ID 

ИЛИ

A.KEY_ID = PUT(B.KEY_ID, 8.) 

Мой вопрос, если длина переменной либо 7 или 8, какой длины я должен поставить после KEY_ID? Я попробовал A.KEY_ID = PUT (B.KEY_ID, 7.), и он потерял все записи с длиной KEY_ID = 8. И когда я использовал A.KEY_ID = PUT (B.KEY_ID, 8.), он не сможет найти соответствующий KEY_ID с длиной = 7.

спасибо!

Добавлено:

Ниже запрос, который я в настоящее время использую. LibnameA - это локальная библиотека, а tableA - локальная таблица SAS. DatabaseB - это база данных, с которой я связан. Столбец Key_id находится в обеих таблицах и используется в качестве ключа для их связывания. Например, key_ids - 1234567, 12345678 и ect.

Когда я использовал следующий запрос, в который я положил длину 7 в конце оператора put, все записи с 8-значными ключами не смогут найти совпадение.

PROC SQL; 
CREATE TABLE LIBNAMEA.WORKTABLE AS 
SELECT 
A.*, 
B.VAR1, 
B.VAR2 
FROM LIBNAMEA.TABLEA A 
LEFT JOIN DATABASEb.TABLEB B 
ON A.KEY_ID = PUT(B.KEY_ID,8.) 
; 
QUIT; 

Update Результаты:

Если я использую следующий запрос, он возвращает 192758 строк

ON A.KEY_ID = PUT(B.KEY_ID,7.) 

Если я использую следующий запрос, он возвращает 192923 строк

ON A.KEY_ID = PUT(B.KEY_ID,8.) 

Если я использую следующий запрос, он возвращает 192757 строк

ON INPUT(A.KEY_ID,8.) = B.KEY_ID 

Если я использую следующий запрос, он возвращает 192757 строк

ON A.KEY_ID = COMPRESS(PUT(B.KEY_ID,8.)) 

Если я использую следующий запрос, он возвращает 192757 строк

ON COMPRESS(A.KEY_ID) = COMPRESS(PUT(B.KEY_ID,8.)) 

Если я использую следующий запрос, он возвращает 192757 строк

ON INPUT(CATS(A.KEY_ID),8.) = INPUT(CATS(B.KEY_ID),8.) 

Если я использую следующий запрос, он возвращает 192757 r РМО

ON A.KEY_ID = PUT(B.KEY_ID,8.-L) 

Как вы можете видеть, только когда я использую ON A.KEY_ID = PUT (B.KEY_ID, 8.), она возвратит 192923 строк, что все строки из таблицы А. Тем не менее, не найдет соответствующие ключевые слова в таблице B и не вернет нулевое значение в конечных результатах.

+0

Скорее всего, у A.KEY_ID нет семизначных строк, хранящихся в ведущих пространствах, но функция PUT() с форматом 8. генерирует ведущие пробелы для числа менее 10 000 000. – Tom

+0

@Tom - Это тоже мое мышление, но OP говорит, что он не работает, когда он удаляет пробелы в критериях соединения. – vknowles

ответ

0

Если вы говорите о целых числах, вам лучше преобразовать значения в числа и сравнить их. Вы можете прочитать строки с 7 символами и строки с 8 символами, используя тот же информационный файл.

input(a.char_key_id,8.) = b.num_key_id 

Относительно того, почему у вас возникли проблемы это, вероятно, из-либо ведущих мест и/или ведущих нулей в версиях символов. Сравнение SAS игнорирует конечные пробелы, поэтому вам не нужно беспокоиться об этом.

Ведущие Ноли

Это большая проблема. Более вероятно, что символьные переменные с ведущими нулями, чем ведущие, так как большинство методов ввода удаляют ведущие пробелы. Но наличие ведущих нулей может привести к тому, что одно целое число имеет несколько представлений символов. Таким образом, вы можете представить 123 как «123», «0123», «00123» и т. Д. Это вызовет проблемы, выходящие за пределы возможности слияния.

Ведущие Пробелы

Это более вероятно, будет проблемой, когда вы пытаетесь конвертировать целые числа в строки. Функция PUT() обычно правильно выравнивает значение (следовательно, оно генерирует ведущее пространство), тогда как большинство методов ввода заканчиваются значением, выровненным слева (конечные пробелы). Поэтому, если вы преобразуете целое число 12345 в строку с использованием put(12345,8.), вы получите три ведущих пробела ' 12345' и не будете соответствовать значению, которое у вас есть в вашей переменной символов, которая имела бы пробелы '12345 '. Вы можете добавить команду выравнивания в формат. И снова, поскольку SAS игнорирует конечные пробелы, вы можете просто использовать более длинный формат.

put(b.num_key_id,F8.-L) = a.char_key_id 

Теперь, если вы не знаете, будут ли ваши переменные числовые или символьные и вы хотите код, который может работать на любой, чем вы могли бы использовать что-то вроде этого, чтобы преобразовать в символ и обратно к цифрам. Но будьте осторожны, если ваши целые числа больше, чем могут быть представлены в 12 цифрах, потому что SAS будет использовать BEST12. формат для преобразования чисел.

+0

Благодарим вас за то, что разделили с нами всю эту информацию. Я попробовал те, которые вы предложили, это не дает того, что я ожидал. Я поделюсь с вами подробными результатами, и, возможно, я смотрю на неправильное направление. Спасибо! –

+0

Покажите некоторые примеры, которые должны соответствовать этому. Также возможно, что в ваших символьных строках есть другие «невидимые» символы, кроме пробелов в них, которые заставляют значения выглядеть одинаково, но быть разными. – Tom

+0

Я думаю, что знаю, почему я не смог получить правильную информацию, когда я использовал ON A.KEY_ID = PUT (B.KEY_ID, 8.). Это так неловко. Я считаю, что это потому, что у меня есть ограничение в конце запроса WHERE B.EXP_DT IS NULL. Я попытался разделить запрос на две части. Сначала я создал другую версию таблицы B, где exp_dt имеет значение null, а затем я оставил присоединенные A и B. Кажется, что это сработало. Мне очень жаль какой-либо путаницы, вызванной этим, потому что я забыл информацию в начале (я думал, что это не имеет значения, и я хочу показать только ту часть запроса, которую я запускал). –

0

Если я понимаю вашу потребность, единственная проблема заключалась в сравнении строковой версии ключей - числовой с INPUT работал, когда я пробовал.

Так что для строковых ключей, это то, что работает для меня:

a.key_id = trim(left(put(b.key_id,8.))) 

Вы можете упростить:

a.key_id = compress(put(b.key_id,8.)) 

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

+0

Привет, спасибо за ваш комментарий. Я попробовал тот, который вы предоставили, и он возвратил те же результаты, как если бы я запустил a.key_id = put (a.key_id, 7.). –

+0

Извините, если я не описал свой вопрос хорошо. Я постараюсь перефразировать его. Ключевой_ID, который я использую, будет либо 7 цифр, либо 8 цифр. В первом я использовал запрос a.key_id = put (a.key_id, 7.), Но все записи с key_id равны 8 цифрам, не смогут найти совпадение. Затем я использовал запрос a.key_id = put (a.key_id, 8.), Но все те, у которых 7 цифр, не могут быть сопоставлены. Я не уверен, почему, и я ищу решение для решения этой проблемы. –

+0

Что делать, если вы используете это: 'compress (a.key_id) = compress (put (b.key_id, 8.))' – vknowles