![]() |
![]() |
![]() |
|
Как определить, что строка состоит ТОЛЬКО из цифр? | ☑ | ||
---|---|---|---|---|
0
Смит
23.10.10
✎
12:38
|
Функцию-то я написал, но может есть более красивый путь?
|
|||
1
zak555
23.10.10
✎
12:40
|
СтрДлина(Число(Стр))=СтрДлина(Стр)
|
|||
2
zak555
23.10.10
✎
12:40
|
?(СтрДлина(Число(Стр))=СтрДлина(Стр), "Числа", "хренушки")
|
|||
3
Андрюха
23.10.10
✎
12:41
|
Если первый символ не "0" то можно так
|
|||
4
zak555
23.10.10
✎
12:42
|
кстати, да
0 вначале надо учитывать |
|||
5
Смит
23.10.10
✎
12:44
|
Ага. Это был первый
|
|||
6
Смит
23.10.10
✎
12:44
|
вариант. Но нули есть.
|
|||
7
Смит
23.10.10
✎
12:45
|
Второй вариант был - сначала замена нулей на "1"
|
|||
8
zak555
23.10.10
✎
12:45
|
(6) в начале ?
|
|||
9
Смит
23.10.10
✎
12:46
|
Потом был еще третий вариант, основанный только на замене.
|
|||
10
Смит
23.10.10
✎
12:46
|
(8) Ага.
|
|||
11
zak555
23.10.10
✎
12:48
|
а в строке могут быть буквы в каких вариантах ?
|
|||
12
Смит
23.10.10
✎
12:50
|
(11) Мне нужно проверять корректность ввода реквизита. Должны быть только цифры.
|
|||
13
zak555
23.10.10
✎
12:51
|
(12) реквизит сделать числом ?
|
|||
14
Тьма
23.10.10
✎
12:52
|
(12)Для этого существует маска ввода
|
|||
15
Смит
23.10.10
✎
12:53
|
(13) Пробовал. Получилось не юзабельно.
(14) Гм. Что это? |
|||
16
zak555
23.10.10
✎
12:54
|
(15) это как ?
|
|||
17
Тьма
23.10.10
✎
12:57
|
||||
18
Смит
23.10.10
✎
12:57
|
(16) Вспомнил. Ведущие нули не вводятся.
|
|||
19
Смит
23.10.10
✎
13:00
|
(17) Спасибо. Помогло.
|
|||
20
Невский Александр
23.10.10
✎
13:03
|
ЭтоЧисло = ИСТИНА;
Для Ном = 0 По СтрДлина(СтрокаКоторуюНадоОпределить) Цикл ТекСимвол = КодСимвола(Сред(Сред(СтрокаКоторуюНадоОпределить),Ном,1)); Если ТекСимвол < 48 ИЛИ ТекСимвол > 57 Тогда ЭтоЧисло = ЛОЖЬ; Прервать; КонецЕсли; КонецЦикла; |
|||
21
Невский Александр
23.10.10
✎
13:03
|
(20) вру ...
Цикл до (СтрокаКоторуюНадоОпределить)-1 |
|||
22
zak555
23.10.10
✎
13:04
|
(20) число может быть отрицательным и дробным =)
|
|||
23
Смит
23.10.10
✎
13:13
|
Дарю свою нетленку. :-)
Стр = СтрЗаменить(Стр, "1", "0"); Стр = СтрЗаменить(Стр, "2", "0"); Стр = СтрЗаменить(Стр, "3", "0"); Стр = СтрЗаменить(Стр, "4", "0"); Стр = СтрЗаменить(Стр, "5", "0"); Стр = СтрЗаменить(Стр, "6", "0"); Стр = СтрЗаменить(Стр, "7", "0"); Стр = СтрЗаменить(Стр, "8", "0"); Стр = СтрЗаменить(Стр, "9", "0"); Стр1 = "0"; Пока СтрДлина(Стр1) <> СтрДлина(Стр) Цикл Стр1 = Стр1 + "0"; КонецЦикла; Если Стр <> Стр1 Тогда Возврат 0; Иначе Возврат 1; КонецЕсли; |
|||
24
kiruha
23.10.10
✎
13:20
|
Неявно 9 циклов, вместо одного(даже меньше если строка) в (20)
|
|||
25
Смит
23.10.10
✎
13:23
|
(24) Угу. Зато читабельно.
|
|||
26
zak555
23.10.10
✎
13:24
|
все про
- . хабыли |
|||
27
Смит
23.10.10
✎
13:29
|
(26) Не забыли. В условии ЦЫФРЫ. "-" и "." нет.
|
|||
28
KishMish
23.10.10
✎
13:29
|
про ноль в начале
Если Строка("1"+ПроверямаяСтрока)=Строка(Число(Строка("1"+ПроверямаяСтрока))) и (26) (НайтиЗапятую и Минус) |
|||
29
big
23.10.10
✎
13:32
|
ГдеИщем="0123456789";
Для а=1 По СтрДлина(Проверяемая) Цикл ТекСимвол=Сред(Проверяемая,а,1); Если Найти(ГдеИщем,ТекСимвол)=0 Тогда Возврат 0; // ошибка, есть НЕ цифры КонецЕсли; КонецЦикла; Возврат 1; // всё ОК, есть только цифры |
|||
30
Torquader
23.10.10
✎
14:41
|
Таки тогда можно и так:
// Предполагается, что ИсходнаяСтрока - строковый реквизит на форме, причём неограниченной длины // Иначе надо сделать TrimRight Если ИсходнаяСтрока="" Тогда Результат="ПустаяСтрока"; ИначеЕсли (СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(ИсходнаяСтрока,"0",""),"1",""),"2",""),"3",""),"4",""),"5",""),"6",""),"7",""),"8",""),"9","")="" Тогда Результат="Верно"; Иначе Результат="Неверно"; КонецЕсли; |
|||
31
Rabbit
23.10.10
✎
15:03
|
(3) пропустит знак и десятичную точку.
|
|||
32
zak555
23.10.10
✎
15:17
|
Функция ЭтоЧисло(Чис)
Если СтрЧислоВхождений(Чис,".")>1 Тогда Возврат 0; КонецЕсли; ЧислоРазМинуса = СтрЧислоВхождений(Чис,"-"); Если ЧислоРазМинуса >1 Тогда Возврат 0; КонецЕсли; Если (ЧислоРазМинуса=1) и (Лев(Чис,1)<>"-") Тогда Возврат 0; КонецЕсли; Для а=1 По СтрДлина(Чис) Цикл ТекСимвол=; Если Найти(0123456789-.",Сред(Чис,а,1))=0 Тогда Возврат 0; КонецЕсли; КонецЦикла; КонецФунцкии |
|||
33
zak555
23.10.10
✎
15:18
|
Функция ЭтоЧисло(Чис)
Если СтрЧислоВхождений(Чис,".")>1 Тогда Возврат 0; КонецЕсли; ЧислоРазМинуса = СтрЧислоВхождений(Чис,"-"); Если ЧислоРазМинуса >1 Тогда Возврат 0; КонецЕсли; Если (ЧислоРазМинуса=1) и (Лев(Чис,1)<>"-") Тогда Возврат 0; КонецЕсли; Для ы=1 По СтрДлина(Чис) Цикл Если Найти(0123456789-.",Сред(Чис,ы,1))=0 Тогда Возврат 0; КонецЕсли; КонецЦикла; КонецФунцкии |
|||
34
Rabbit
23.10.10
✎
15:26
|
8)
|
|||
35
Torquader
23.10.10
✎
15:40
|
Мы как всегда не видим разницы между "Число" и "Строка только из цифр".
Причём, число 0001 и 001 - это одно и то же число, а вот строки-то уже разные. P.S. видимо, разговор идёт о штрих-кодах - там цифр больше, чтобы влазить в четыре байта, а также могут быть ведущие нули - вот и приходится работать с такими "строками". |
|||
36
andrewks
23.10.10
✎
16:23
|
а про Формат-то что никто не вспомнил? ловите
Функция ЭтоЧисло(Стр) Если (Формат(Число(Стр),"Ч (0)"+СокрЛП(СтрДлина(Стр)))<>Стр) ИЛИ (Лев(Стр,1)="-") Тогда // не строка из цифр Возврат 0; Иначе Возврат 1; КонецЕсли; КонецФункции |
|||
37
Torquader
23.10.10
✎
16:33
|
Кстати.
Предположим, что в строке тысяча цифр в случайном порядке - как будет выполняться оператор Число() - и будет ли вообще выполняться ? |
|||
38
Torquader
23.10.10
✎
16:40
|
Выполняем такой код:
s=""; For i=1 To 1000 Do s=s+"1"; EndDo; r=Number(s); s1=String(r); If s1<>s Then t=CreateObject("Text"); t.AddLine("Не совпало!"); t.AddLine("Было:"+s); t.AddLine("Стало:"+s1); t.Write(IBDir()+"123.txt"); EndIf; Получаем такой файл. Не совпало! Было:1111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111111 Стало:1111111111111111111111111111111111111111111111111111111111111111 Как бы, предполагается задуматься над использованием функции "Число" - уж очень она "неудачная". |
|||
39
andrewks
23.10.10
✎
16:44
|
(37) ну вот, опять пришел поручик Ржевский и все опо.лил...
на длине строки = 65 ломается, но если это штрих-код то там не больше 13-ти, для них-то сойдет |
|||
40
G-Re
23.10.10
✎
17:21
|
Может быть где-то так?
сзЦифры=СоздатьОбъект("СписокЗначений"); сзНеЦифры=СоздатьОбъект("СписокЗначений"); Для ц=0 то 9 Цикл сзЦифры.ДобавитьЗначение(""+ц); КонецЦикла; Размер=СтрДлина(СтрокаВвода); Для ц=1 по Размер Цикл тЗнач=Сред(СтрокаВвода,ц,1); Если сзЦифры.Принадлежит(тЗнач)=0 Тогда сзНеЦифры.ДобавитьЗначение(ц,тЗнач); КонецЕсли; КонецЦикла; Таким образом, сзНеЦифры содержит все позиции с нецифрами и конкретно какими, Если сзНеЦифры.РазмерСписка()=0 Значит все цифры. Легко обобщается на случай, когда в строке должны быть только определенные символы, которыми нужно заполнить сзЦифры. |
|||
41
Mikeware
23.10.10
✎
17:28
|
Ну тогда уж РегВыражения юзать....
|
|||
42
Torquader
23.10.10
✎
17:33
|
(40) Вместо списка значений на допустимые символы лучше использовать строку, как в (29) - а так, задумка очень правильная.
|
|||
43
G-Re
23.10.10
✎
17:43
|
(42) Согласен, просто не знаю, что быстрей отрабатывает,
Найти или Принадлежит, мне показалось, что второе. Но предложил вариант, как некий типовый алгоритм, инструменты можно менять по вкусу. Те же нецифры можно собирать и в ТЗ и в Строке, да где угодно, хоть в справочнике:). |
|||
44
Torquader
23.10.10
✎
17:52
|
(43) Если надо часто сравнивать, то мы делаем просто:
Массив на 255 элементов - где 1, если символ допустим и 0, если нет, а далее перебираем строку и ищем коды символов в этом массиве - должно быть быстрее любого поиска. |
|||
45
Эмбеддер
23.10.10
✎
18:19
|
если ПустаяСтрока(Стр)=0 тогда
если СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(СтрЗаменить(Стр,"0",""),"1",""),"2"....)="" тогда Сообщить("Только цифры"); конецесли; конецесли; |
|||
46
Эмбеддер
23.10.10
✎
18:20
|
(43) Хотя в (30) уже это было...
|
|||
47
G-Re
23.10.10
✎
18:22
|
(44) Согласен, на заре программирования, в эпоху неразвитых языков высокого уровня это был, по сути, единстенный достойный вариант, да и сейчас по скорости он, по-видимому, лидер, так как индекс элемента массива уже есть - КодСимв(ТекСимвол).
|
|||
48
Torquader
23.10.10
✎
18:25
|
На заре программирования 256 байт на какой-то массив было жалко (а ведь его ещё чем-то заполнять надо).
|
|||
49
kiruha
23.10.10
✎
18:28
|
А еще быстрее разбить строку на подстроки,
и запустить параллельные процессы проверки подстрок на число. Если хотя бы одна подстрока не число - не число |
|||
50
G-Re
23.10.10
✎
18:46
|
(48)256/8=32байта. Конечно, побитное представление.
(49) А разве 1С может параллелить? Как, не знаю, подскажите. |
|||
51
kiruha
23.10.10
✎
18:53
|
(50)
1С не может. Свою компоненту написать |
|||
52
G-Re
23.10.10
✎
18:57
|
(51) Ну да..., особенно для того, что бы узнать, есть ли в строке нецифры...
|
|||
53
Torquader
23.10.10
✎
19:29
|
(51) Вы ещё про кодировку вспомните.
Слава богу, что в семёрке только одна кодировка. |
|||
54
Шурик71
23.10.10
✎
19:36
|
Как, еще никто регекспы не предложил?!
|
|||
55
andrewks
23.10.10
✎
19:40
|
(54) читай внимательнее O_O
|
|||
56
Эмбеддер
23.10.10
✎
21:07
|
(53) Цифры могут быть только одного алфавита - нашего, т.е. арабского )))
|
|||
57
andrewks
23.10.10
✎
21:14
|
(56) а как же римские? ;)
|
|||
58
orefkov
23.10.10
✎
21:15
|
||||
59
Барбариска
23.10.10
✎
21:16
|
Функция ЧислоИзСтроки(Знач Стр) Экспорт
Стр = СтрЗаменить(Стр,Симв(34),""); Сп = СоздатьОбъект("СписокЗначений"); Сп.ИзСтрокиСРазделителями(Стр); Если Сп.Размерсписка()>0 Тогда Возврат Сп.ПолучитьЗначение(1) КонецЕсли; Возврат ""; КонецФункции Сравнить "1"+Строка+"1" и ЧислоИзСтроки("1"+Строка+"1") Ну и еще на вхождение дробного разделителя проверить... |
|||
60
Эмбеддер
23.10.10
✎
21:18
|
(57) Мощности не хватит. Заметили, что в паспорте серия теперь тоже арабскими?
|
|||
61
andrewks
23.10.10
✎
21:19
|
(60) ага заметил. мощности не хватило видимо у компов ФМС, а у нас и мощности, и мозгов хватит
|
|||
62
andrewks
23.10.10
✎
21:24
|
(59) а что, 123"45 тоже число? каков глубинный смысл в
Стр = СтрЗаменить(Стр,Симв(34),"")? |
|||
63
Барбариска
23.10.10
✎
21:28
|
(62) :) ну да, внутренние кавычки.... это тоже вариант
правильнее просто замена крайних символов - если кавычки |
|||
64
andrewks
23.10.10
✎
21:30
|
(63) гмм... ну вроде "12345" тоже не число, надо 12345
|
|||
65
Эмбеддер
23.10.10
✎
21:30
|
Если в строке есть кавычки, она состоит не только из цифр, но и кавычек. Это не правильно
|
|||
66
Эмбеддер
23.10.10
✎
21:31
|
Понял, не заметил пример вызова
|
|||
67
Барбариска
23.10.10
✎
21:32
|
ок, убираем про кавычки )))
|
|||
68
smaharbA
23.10.10
✎
21:32
|
вечная тема
|
|||
69
andrewks
23.10.10
✎
21:35
|
(59) чем больше я смотрю на содержимое Функция ЧислоИзСтроки
тем меньше я в ней понимаю ... |
|||
70
Torquader
23.10.10
✎
21:38
|
(69) Так ведь - "получить число из строки с цифрами" и "проверить, что в строке только цифры" - это две совершенно разные задачи.
|
|||
71
Барбариска
23.10.10
✎
21:39
|
(69) тем не менее.. потестируй )) убрав строчку про кавычки
|
|||
72
andrewks
23.10.10
✎
21:41
|
(70) согласен, я вообще не об этом, просто я раньше никогда не замечал такое странное поведение функции ИзСтрокиСРазделителями. оказывается для "эюя345" она выдает число 345, тогда как Число("эюя345")=0. Кто-нибудь видел это в описании или я один такой слепой?
|
|||
73
Эмбеддер
23.10.10
✎
21:45
|
(72) Скорее всего Барбариска использует эту функцию когда выводит на печать номер документа, удаляя его префикс
|
|||
74
andrewks
23.10.10
✎
21:51
|
(71) во-первых, сравнивать надо с Строка(ЧислоИзСтроки("1"+Стр+"1")), а во-вторых эта функция слетает уже со строк длины 63, тогда как моя - только с длины 65 :)))
|
|||
75
andrewks
23.10.10
✎
22:57
|
я тут от нечего делать решил потестить предложенные варианты по быстродействию (эх, ностальгия прошибла, прям как в школе лабы делали), изначально полагал что самый быстрый д.б. (20) (по крайней мере при реализации ч/з массив в нормальном ЯП).
давал на вход 50 тыс. строк, содержащих только цифири, длиной 60. оказалось: почти все варианты с использованием строковых процедур (20) (23) (29) (33) дали длительность 50-60, вариант (59) - 68, (40) - 175! (ессесно я вынес формирование списка цифр за функцию), (30) - 34-35 (хотя когда я первый раз на него взглянул, подумал - тормозной), (36) - 34-35. т.к. у меня длины проверяемых строк не больше 20, решил оставить свой вариант - он на мой взгляд покрасивше (30) |
|||
76
smaharbA
23.10.10
✎
23:06
|
(75)
36,6 это строка или число ? |
|||
77
smaharbA
23.10.10
✎
23:07
|
а 36 000 это строка или число ?
|
|||
78
andrewks
23.10.10
✎
23:10
|
по условиям сабжа: мы проверяем, содержит ли строка только цифры.
|
|||
79
smaharbA
23.10.10
✎
23:14
|
(78) слабое оправдание
|
|||
80
smaharbA
23.10.10
✎
23:15
|
для этого и формт то не нужен
0+чето = чето |
|||
81
andrewks
23.10.10
✎
23:17
|
(79) это не оправдание, это условие. у меня моя функция используется в наборе процедур проверки некоторых реквизитов по ключу (ИНН, ОГРН и т.д.), там в принципе нет чисел, есть строчки, которые должны содержать только цифры.
|
|||
82
andrewks
23.10.10
✎
23:19
|
(80) не вкурил...
|
|||
83
Torquader
23.10.10
✎
23:21
|
(75) А с массивом кодов проверял ?
Хотя, есть мнение, что выбор строки Сред(Строка,Позиция,1) уже достаточно тормозная операция. (в javascript есть charCodeAt(Position) и он побыстрее). Замена же оказалась быстрой из-за того, что длины строк совпадали - тогда она сводится к Search&Replace. |
|||
84
andrewks
23.10.10
✎
23:22
|
(83) с массивом кодов - это как?
|
|||
85
andrewks
23.10.10
✎
23:25
|
+(84) у меня давно уже сложилось впечатление, что строковые функции в 1С далеки от оптимальности.
|
|||
86
Torquader
23.10.10
✎
23:26
|
(80)
Проверил таким кодом - не взлетело. i=1; j="1"; If i=j Then Message("Круто");EndIf; Так тоже: i="1"; If 0+i=i Then Message("А так");EndIf; |
|||
87
Torquader
23.10.10
✎
23:28
|
(84) Вот так:
// подготовительный этап Var CharArr[255]; For i=1 To 255 Do CharArr[i]=0;EndDo; For i=48 To 57 Do CharArr[i]=1;EndDo; // Function ThisIsNumString(StringForTest) l=StrLen(StringForTest); For i=1 To l Do If CharArr[Asc(Mid(StringForTest,i,1))]<>1 Then Return 0;EndIf; EndDo; Return 1; EndFunction |
|||
88
andrewks
23.10.10
✎
23:30
|
(87) а-а-а понятно, ява. я принципиально тестил только алгоритмы так сказать на plain 1C
|
|||
89
smaharbA
23.10.10
✎
23:33
|
(86) а ты ум наморщи
|
|||
90
andrewks
23.10.10
✎
23:33
|
+(88) ява -> скрипт
|
|||
91
smaharbA
23.10.10
✎
23:34
|
(90) в (87) что ни на есть адинес
|
|||
92
Torquader
23.10.10
✎
23:35
|
(88) Таки это тот же самый 1С, только по английски.
Перем МассСимв[255]; Для i=1 По 255 Цикл МассСимв[i]=0;КонецЦикла; Для i=48 По 57 Цикл МассСимв[i]=1;КонецЦикла; Функция ЭтоЧисловаяСтрока(Стр) Дл=ДлинаСтроки(Стр); Для ТекПоз=1 По Дл Цикл Если МассСимв[КодСимв(Сред(Стр,ТекПоз,1))]<>1 Тогда Возврат 0;КонецЕсли; КонецЦикла; Возврат 1; КонецФункции |
|||
93
andrewks
23.10.10
✎
23:37
|
(91) во блин глаза замылило по ходу спать пора...
|
|||
94
Torquader
23.10.10
✎
23:42
|
(89) Ты хотел сказать, что
Число(ПроверяемаяСтрока+"0")/10=Число(ПроверяемаяСтрока) Так что-ли ? |
|||
95
andrewks
23.10.10
✎
23:43
|
(92) длительность - 48-52 + дополнительная нехилая структура с заполнением. прямо класс - данные, конструктор, метод
|
|||
96
Torquader
23.10.10
✎
23:44
|
(95) Структуру надо вызывать только один раз - перед началом использования.
|
|||
97
andrewks
23.10.10
✎
23:45
|
(96) ессесно так и делал
|
|||
98
andrewks
23.10.10
✎
23:49
|
(94) длительность - 33-34, но не учитывает минус. вот так:
Функция ЭтоЧисло10(Стр) Если (Число(Стр+"0")/10=Число(Стр)) И (Лев(Стр,1)<>"-") Тогда Возврат 1; Иначе Возврат 0; КонецЕсли; КонецФункции |
|||
99
andrewks
23.10.10
✎
23:52
|
+(98) и кстати не падает после 65-симв.строк. красиво!
|
|||
100
andrewks
23.10.10
✎
23:53
|
бли-и-ин! сломалось на "а1234"
|
|||
101
andrewks
23.10.10
✎
23:56
|
ну да все верно число(бяка+0)=0 / 10 = 0 = число (бяка) = 0
|
|||
102
Torquader
24.10.10
✎
00:17
|
Тогда
Число(Бяка)*10+1=Число(Бяка+1) |
|||
103
andrewks
24.10.10
✎
20:58
|
(102) не понял...
|
|||
104
Сигизмунд Прокофьеви
24.10.10
✎
21:23
|
регулярные выражения не предлагать?
|
|||
105
andrewks
24.10.10
✎
21:25
|
(104) блин, третий раз уже... читай лучше O_O
|
|||
106
Torquader
24.10.10
✎
21:48
|
(103)
Точнее так: Если Число(НашаСтрока)*10+1=Число(НашаСтрока+"1") Тогда "Ура"; То есть если у нас число (причём целое), то мы просто умножаем его на 10 и прибавляем единицу. Если число записано строкой, то действие - добавить единицу в конец. Если не число, то 0*10+1=1 Число(Фигня+"1")=0 Но, надо учитывать, что функция Число получит число из строки " 123" (то есть пробелы в начале будут отброшены). Другими словами, нам данное решение не подходит. |
|||
107
zak555
24.10.10
✎
22:18
|
так где правильно ?
|
|||
108
Мимохожий Однако
24.10.10
✎
22:26
|
(107) см.(80) "Доступно и всерьез"
|
|||
109
zak555
24.10.10
✎
22:35
|
(108) хня
|
|||
110
andrewks
24.10.10
✎
22:36
|
(108) шютник...
|
Форум | Правила | Описание | Объявления | Секции | Поиск | Книга знаний | Вики-миста |