RStudio обрезает длинные строки при вставке в IDE — обходной путь?

#r #rstudio

#r #rstudio

Вопрос:

Я использую R 3.6.1 и RStudio 1.3.1056.

При вставке длинной символьной строки в RStudio с использованием paste() или paste0() или даже c() или просто присваивания строки объекту я получаю некоторые странные результаты, и они выглядят уникальными для RStudio (если вы размещаете этот код непосредственно в R, он работает просто отлично; для nchar() указано правильное значение):

 thing <- paste0("(blah blah
                '100869017', '100895297', '100937037', '100952542', '100953872', '100958290', '100977291', '100978521', '100982570', '100983764', '100986439', '100987969', '100988635', '100988637', '100989748', '100992594', '100998300', '100998306', '101000068', '101000556', '101002036', '101002550', '101002813', '101002871', '101002872', '101003492', '101003787', '101003789', '101003830', '101004348', '101004349', '101004400', '101004401', '101005323', '101005738', '101006388', '101006411', '101006413', '101006414', '101006416', '101006417', '101006419', '101006440', '101006441', '101006442', '101006443', '101006444', '101006445', '101006446', '101006447', '101006448', '101006449', '101006450', '101006451', '101006452', '101006453', '101006454', '101006455', '101006456', '101006457', '101006458', '101006554', '101006588', '101006608', '101008736', '101009658', '101011518', '101011680', '101011681', '101012457', '101012495', '101014157', '101014197', '101014240', '101014244', '101014248', '101014301', '101014302', '101014303', '101014304', '101014358', '101014480', '101014481', '101015219', '101017560', '101019383', '101019396', '101019454', '101019480', '101019481', '101019567', '101020977', '101022585', '101024007', '101024436', '101028376', '101028377', '101028405', '101029814', '101030739', '101030940', '101031364', '101031368', '101032356', '101032399', '101032440', '101032441', '101032442', '101032443', '101032444', '101032462', '101032468', '101032482', '101032483', '101032484', '101032485', '101032486', '101032487', '101032488', '101032489', '101032590', '101032591', '101032735', '101032987', '101033456', '101036227', '101037275', '101038196', '101038279', '101038930', '101038932', '101038938', '101039576', '101041116', '101041233', '101041288', '101042815', '101043166', '101043280', '101043281', '101043282', '101043285', '101043288', '101043307', '101043302', '101043329', '101043405', '101043837', '101045392', '101045635', '101046419', '101046440', '101046441', '101047082', '101047224', '101047227', '101047275', '101047281', '101047286', '101047287', '101047288', '101047290', '101047293', '101047295', '101047297', '101047304', '101048355', '101048439', '101048480', '101048905', '101048921', '101050905', '101052305', '101052442', '101052448', '101052449', '101052480', '101052481', '101052485', '101052487', '101052489', '101052522', '101052550', '101052551', '101053187', '101055017', '101055036', '101055039', '101055220', '101055258', '101055313', '101055316', '101055317', '101059567', '101060256', '101060554', '101060810', '101060817', '101061738', '101061739', '101061762', '101062369', '101062469', '101063528', '101063909', '101065440', '101065471', '101065473', '101065536', '101065760', '101065784', '101065805', '101065813', '101068343', '101068346', '101069329', '101069472', '101069478', '101069771', '101069871', '101069902', '101070895', '101071301', '101071303', '101072911', '101072914', '101072915', '101072944', '101072946', '101072949', '101072972', '101072981', '101072984', '101072985', '101073389', '101073806', '101074467', '101074469', '101074650', '101074709', '101074721', '101074869', '101075639', '101075881', '101075887', '101075888', '101076841', '101076843', '101076884', '101076885', '101076889', '101076930', '101077036', '101077872', '101077877', '101078006', '101078141', '101078834', '101079626', '101079624', '101079658', '101080128', '101080146', '101080341', '101080389', '101080732', '101080738', '101080931', '101081744', '101081745', '101082123', '101082443', '101082445', '101082447', '101085919', '101086763', '101086774', '101086801', '101086915', '101086964', '101086965', '101087006', '101088057', '101088465', '101089884', '101089915', '101089945', '101090159', '101090197', '101090225', '101090226', '101090227', '101090229', '101090293', '101091218', '101091232', '101091238', '101091239', '101091635', '101091655', '101092773', '101092997', '101093029', '101093064', '101093067', '101093255', '101093344', '101097283', '101097668', '101098444', '101098514', '101099068', '101099073', '101099076', '101099141', '101099170', '101099172', '101099173', '101099175', '101099177', '101099178', '101099194', '101099204', '101099206', '101099581', '101099666', '101100002', '101100179', '101100492', '101100617', '101101080', '101101088', '101101091', '101101092', '101101115', '101101117', '101101150', '101101158', '101102050', '101102086', '101102101', '101102108', '101102169', '101102650', '101102712', '101103376', '101106299', '101106618', '101107257', '101107277', '101108114', '101108119', '101108670', '101108702', '101108707', '101109772', '101109774', '101109779', '101111022', '101111029', '101113873', '101114376', '101114390', '101115163', '101115246', '101115247', '101115357', '101115358', '101116813', '101116819', '101116870', '101116877', '101118108', '101118175', '101118178', '101118277', '101118441', '101118449', '101118471', '101118505', '101118631', '101119051', '101119448', '101119914', '101120073', '101120076', '101120127', '101120292', '101120334', '101120387', '101120389', '101122367', '101122822', '101122881', '101122886', '101124670', '101124838', '101125490', '101125610', '101126329', '101127340', '101127341', '101127342', '101127343', '101127346', '101127347', '101127360', '101127853', '101127855', '101127856', '101127857', '101128128', '101128126', '101128132', '101128135', '101130135', '101131523', '101132622', '101132648', '101132850', '101132870', '101132931', '101132938', '101132990', '101132994', '101133104', '101133206', '101133248', '101134597', '101134599', '101134611', '101134649', '101134661', '101134704', '101134771', '101135221', '101135276', '101135278', '101135409', '101135444', '101135518', '101135630', '101135633', '101135632', '101137571', '101137750', '101137812', '101137875', '101138237', '101139907', '101139931', '101139968', '101140076', '101140148', '101140181', '101140250', '101140253', '101140460', '101140462', '101140466', '101140469', '101140518', '101150986', '101150987', '101150990', '101150994', '101150995', '101151373', '101151376', '101151416', '101151418', '101151419', '101151434', '101151437', '101151891', '101151974', '101151978', '101151979', '101151996', '101152030', '101152031', '101152032', '101152037', '101152062', '101152063', '101152066', '101152068', '101152069', '101152070', '101152072', '101152073', '101152074', '101152077', '101152078', '101152080', '101152081', '101152083', '101152085', '101152087', '101152088', '101152089', '101152100', '101152103', '101152105', '101153684', '101153944', '101153966', '101153996', '101153999', '101155013', '101155141', '101155149', '101155311', '101155560', '101155880', '101155882', '101155883', '101155884', '101155905', '101156458', '101156459', '101156511', '101156524', '101156546', '101156547', '101156596', '101156611', '101156641', '101156664', '101156752', '101156786', '101156801', '101156842', '101156885', '101156888', '101156892', '101157753', '101157844', '101157881', '101157905', '101157927', '101158001', '101158011', '101158025', '101158028', '101158034', '101158061', '101158081', '101158084', '101158103', '101158107', '101159736', '101160183', '101160203', '101160234', '101160373', '101160377', '101160381', '101160378', '101160451', '101160551', '101162202', '101162245', '101162247', '101162249', '101162492', '101162538', '101162585', '101162595', '101162627', '101162630', '101162634', '101162792', '101162848', '101162876', '101162904', '101164138', '101164337', '101165132', '101165133', '101165134'
                blah blah)")
nchar(thing)
  

Результат nchar() равен 4130. На самом деле nchar() должно отображаться 7603.

Зачем мне делать что-то подобное в скрипте? В данном случае это был SQL-запрос, записанный в скрипт и выполняемый через RStudio.

Еще более странным является удаление «бла-бла-бла» вверху и внизу строки:

 thing <- paste0("'100869017', '100895297', '100937037', '100952542', '100953872', '100958290', '100977291', '100978521', '100982570', '100983764', '100986439', '100987969', '100988635', '100988637', '100989748', '100992594', '100998300', '100998306', '101000068', '101000556', '101002036', '101002550', '101002813', '101002871', '101002872', '101003492', '101003787', '101003789', '101003830', '101004348', '101004349', '101004400', '101004401', '101005323', '101005738', '101006388', '101006411', '101006413', '101006414', '101006416', '101006417', '101006419', '101006440', '101006441', '101006442', '101006443', '101006444', '101006445', '101006446', '101006447', '101006448', '101006449', '101006450', '101006451', '101006452', '101006453', '101006454', '101006455', '101006456', '101006457', '101006458', '101006554', '101006588', '101006608', '101008736', '101009658', '101011518', '101011680', '101011681', '101012457', '101012495', '101014157', '101014197', '101014240', '101014244', '101014248', '101014301', '101014302', '101014303', '101014304', '101014358', '101014480', '101014481', '101015219', '101017560', '101019383', '101019396', '101019454', '101019480', '101019481', '101019567', '101020977', '101022585', '101024007', '101024436', '101028376', '101028377', '101028405', '101029814', '101030739', '101030940', '101031364', '101031368', '101032356', '101032399', '101032440', '101032441', '101032442', '101032443', '101032444', '101032462', '101032468', '101032482', '101032483', '101032484', '101032485', '101032486', '101032487', '101032488', '101032489', '101032590', '101032591', '101032735', '101032987', '101033456', '101036227', '101037275', '101038196', '101038279', '101038930', '101038932', '101038938', '101039576', '101041116', '101041233', '101041288', '101042815', '101043166', '101043280', '101043281', '101043282', '101043285', '101043288', '101043307', '101043302', '101043329', '101043405', '101043837', '101045392', '101045635', '101046419', '101046440', '101046441', '101047082', '101047224', '101047227', '101047275', '101047281', '101047286', '101047287', '101047288', '101047290', '101047293', '101047295', '101047297', '101047304', '101048355', '101048439', '101048480', '101048905', '101048921', '101050905', '101052305', '101052442', '101052448', '101052449', '101052480', '101052481', '101052485', '101052487', '101052489', '101052522', '101052550', '101052551', '101053187', '101055017', '101055036', '101055039', '101055220', '101055258', '101055313', '101055316', '101055317', '101059567', '101060256', '101060554', '101060810', '101060817', '101061738', '101061739', '101061762', '101062369', '101062469', '101063528', '101063909', '101065440', '101065471', '101065473', '101065536', '101065760', '101065784', '101065805', '101065813', '101068343', '101068346', '101069329', '101069472', '101069478', '101069771', '101069871', '101069902', '101070895', '101071301', '101071303', '101072911', '101072914', '101072915', '101072944', '101072946', '101072949', '101072972', '101072981', '101072984', '101072985', '101073389', '101073806', '101074467', '101074469', '101074650', '101074709', '101074721', '101074869', '101075639', '101075881', '101075887', '101075888', '101076841', '101076843', '101076884', '101076885', '101076889', '101076930', '101077036', '101077872', '101077877', '101078006', '101078141', '101078834', '101079626', '101079624', '101079658', '101080128', '101080146', '101080341', '101080389', '101080732', '101080738', '101080931', '101081744', '101081745', '101082123', '101082443', '101082445', '101082447', '101085919', '101086763', '101086774', '101086801', '101086915', '101086964', '101086965', '101087006', '101088057', '101088465', '101089884', '101089915', '101089945', '101090159', '101090197', '101090225', '101090226', '101090227', '101090229', '101090293', '101091218', '101091232', '101091238', '101091239', '101091635', '101091655', '101092773', '101092997', '101093029', '101093064', '101093067', '101093255', '101093344', '101097283', '101097668', '101098444', '101098514', '101099068', '101099073', '101099076', '101099141', '101099170', '101099172', '101099173', '101099175', '101099177', '101099178', '101099194', '101099204', '101099206', '101099581', '101099666', '101100002', '101100179', '101100492', '101100617', '101101080', '101101088', '101101091', '101101092', '101101115', '101101117', '101101150', '101101158', '101102050', '101102086', '101102101', '101102108', '101102169', '101102650', '101102712', '101103376', '101106299', '101106618', '101107257', '101107277', '101108114', '101108119', '101108670', '101108702', '101108707', '101109772', '101109774', '101109779', '101111022', '101111029', '101113873', '101114376', '101114390', '101115163', '101115246', '101115247', '101115357', '101115358', '101116813', '101116819', '101116870', '101116877', '101118108', '101118175', '101118178', '101118277', '101118441', '101118449', '101118471', '101118505', '101118631', '101119051', '101119448', '101119914', '101120073', '101120076', '101120127', '101120292', '101120334', '101120387', '101120389', '101122367', '101122822', '101122881', '101122886', '101124670', '101124838', '101125490', '101125610', '101126329', '101127340', '101127341', '101127342', '101127343', '101127346', '101127347', '101127360', '101127853', '101127855', '101127856', '101127857', '101128128', '101128126', '101128132', '101128135', '101130135', '101131523', '101132622', '101132648', '101132850', '101132870', '101132931', '101132938', '101132990', '101132994', '101133104', '101133206', '101133248', '101134597', '101134599', '101134611', '101134649', '101134661', '101134704', '101134771', '101135221', '101135276', '101135278', '101135409', '101135444', '101135518', '101135630', '101135633', '101135632', '101137571', '101137750', '101137812', '101137875', '101138237', '101139907', '101139931', '101139968', '101140076', '101140148', '101140181', '101140250', '101140253', '101140460', '101140462', '101140466', '101140469', '101140518', '101150986', '101150987', '101150990', '101150994', '101150995', '101151373', '101151376', '101151416', '101151418', '101151419', '101151434', '101151437', '101151891', '101151974', '101151978', '101151979', '101151996', '101152030', '101152031', '101152032', '101152037', '101152062', '101152063', '101152066', '101152068', '101152069', '101152070', '101152072', '101152073', '101152074', '101152077', '101152078', '101152080', '101152081', '101152083', '101152085', '101152087', '101152088', '101152089', '101152100', '101152103', '101152105', '101153684', '101153944', '101153966', '101153996', '101153999', '101155013', '101155141', '101155149', '101155311', '101155560', '101155880', '101155882', '101155883', '101155884', '101155905', '101156458', '101156459', '101156511', '101156524', '101156546', '101156547', '101156596', '101156611', '101156641', '101156664', '101156752', '101156786', '101156801', '101156842', '101156885', '101156888', '101156892', '101157753', '101157844', '101157881', '101157905', '101157927', '101158001', '101158011', '101158025', '101158028', '101158034', '101158061', '101158081', '101158084', '101158103', '101158107', '101159736', '101160183', '101160203', '101160234', '101160373', '101160377', '101160381', '101160378', '101160451', '101160551', '101162202', '101162245', '101162247', '101162249', '101162492', '101162538', '101162585', '101162595', '101162627', '101162630', '101162634', '101162792', '101162848', '101162876', '101162904', '101164138', '101164337', '101165132', '101165133', '101165134'")
  

В этом случае консоль зависает с , как будто ожидая дальнейшего ввода.

Опять же, возьмите эти примеры и поместите их непосредственно в R и nchar() получите правильное количество.

Хуже всего то, что в первом примере объект создан, но усечен, а последняя часть строки сохраняется, то есть окончание «бла-бла-бла». Это привело к тому, что SQL-запросы исключали некоторые критерии — более 3400 символов критериев!

Если бы кто-нибудь сказал, что это уродливый способ написания SQL-запросов, я бы согласился. И я, конечно, не хотел бы, чтобы где-либо в моем коде была одна строка такой длины, но есть большая вероятность, что они могут появиться в командной среде, где пользователь менее знаком с R и RStudio. RStudio не выдает абсолютно никакого индикатора или предупреждения о том, что это сделано, насколько я могу судить.

Есть ли какой-либо способ избежать такого поведения, кроме разделения строк или поиска SQL-скриптов или текстовых файлов?

Комментарии:

1. Я больше удивлен, что это работает в R, чем тем, что это не работает в RStudio. R имеет жестко запрограммированное CONSOLE_BUFFER_SIZE значение 4095, так что это должна быть максимальная длина строки. Должно быть, происходит что-то странное, когда у вас есть строка, которая занимает несколько строк (имеет литерал новой строки внутри).

2. Дополнительное замечание, которое может обойти проблему: я каждый день сталкиваюсь с SQL и активно избегаю включения «данных» в саму строку запроса. Я предпочитаю «привязку параметров». Это не идеально, но если ваш вектор vec , то, возможно DBI::dbGetQuery(con, paste("select ... where id in (", paste(rep("?", length(vec)), collapse = ","), ")"), params = as.list(vec)) .

3. @r2evans, наверняка есть более чистые способы выполнения запросов. Обычно я предпочитаю записывать свой запрос в виде файла .sql и запускать что-то вроде « запрос <- readLines(«my_query.sql») q_result <- odbc::dbGetQuery(con, paste0(запрос, collapse = «n»)) Но работать в командной среде с людьми, которые привыкли к SAS или STATA и которые копируют строку из notepad и вставляют ее в RStudio, ожидая, что она сработает, и не получают никаких указаний на то, что она не сработала — это проблематично.

4. Я понимаю, и я согласен. Моя точка зрения в основном касается защиты от случайного sql-внедрения и немного о том, чтобы позволить оптимизаторам запросов выполнять свою работу. Извините, что отвлекаю, я вижу вашу дилемму и мне нечего предложить по проблеме ширины символа.

5. @r2evans, я понял. Нет проблем. Спасибо!