Скрипты для Demagog
Модератор: flegont
- tonio_k
- V.I.P.
Скрипты для Demagog
как раз это можно реализовать через скрипты. Можно сделать подобие швейцарского ножа с кучей вариантов и повесить его только на одну комбинацию клавиш. Нажимаете комбинацию клавиш к выделенному тексту, выйдет окно для работы с выделенным текстом. Если текст был не выделен, то выйдет окно с вариантами действий для всего содержимого окна. Тут большой простор для полета фантазии и возможностей. Вот простой пример шаблона окна:
http://i91650e3.beget.tech/viewtopic.php?p=4792#p4628
Самое главное, пункты меню вы можете подобрать для себя индивидуально только то что вам хочется и с чем вам удобно работать. А со временем можно пункты убрать или новые добавить. Т.е. вы сами управляете интерфейсом и пунктами меню, а не подстраиваетесь под имеющийся у редактора. Пишите в ЛС обсудим.
- VitalijBurenko
- Прохожий
Скрипты для Demagog
Ребята здравствуйте.
Простите если не в ту ветку пишу.
Есть необходимость озвучивать стартовый протокол на спортивных соревнованиях.
Протокол генерируется программно.
Каждая его строка содержит стартовую минуту и набор фамилий.
Подскажите как наиболее легко из него получить либо один длинный файл но чтобы в нем каждая строка начинала воспроизводится четко со своей минуты.
Либо пачку файлов с озвучкой только одной строки.
Пример файла:
1, Произвольный текст 1
2, Произвольный текст 2
.....
5, Произвольный текст 5
7, Произвольный текст 7
Нужно получить либо 1 файл в котором на первой минуте звучит "Произвольный текст 1" на второй "Произвольный текст 2" и т.д.
Либо 7 файлов . 1.mp3 - c озвучкой "Произвольный текст 1" , 2.mp3 - c озвучкой "Произвольный текст 2" и т.д.
Просто с синтезом речи столкнулся впервые и не совсем понимаю как это сделать правильней.
Простите если не в ту ветку пишу.
Есть необходимость озвучивать стартовый протокол на спортивных соревнованиях.
Протокол генерируется программно.
Каждая его строка содержит стартовую минуту и набор фамилий.
Подскажите как наиболее легко из него получить либо один длинный файл но чтобы в нем каждая строка начинала воспроизводится четко со своей минуты.
Либо пачку файлов с озвучкой только одной строки.
Пример файла:
1, Произвольный текст 1
2, Произвольный текст 2
.....
5, Произвольный текст 5
7, Произвольный текст 7
Нужно получить либо 1 файл в котором на первой минуте звучит "Произвольный текст 1" на второй "Произвольный текст 2" и т.д.
Либо 7 файлов . 1.mp3 - c озвучкой "Произвольный текст 1" , 2.mp3 - c озвучкой "Произвольный текст 2" и т.д.
Просто с синтезом речи столкнулся впервые и не совсем понимаю как это сделать правильней.
- balabolka
- V.I.P.
Скрипты для Demagog
Проще всего создать файл формата LRC и преобразовать его в аудиофайл в Балаболке (или при помощи консольной утилиты "Балаболки").VitalijBurenko писал(а): ↑05 дек 2020 22:05Подскажите как наиболее легко из него получить либо один длинный файл но чтобы в нем каждая строка начинала воспроизводится четко со своей минуты.
Файл формата LRC (с именем, например, FILE.LRC) будет выглядеть так:
Код: Выделить всё
[00:00.00]Произвольный текст 1
[01:00.00]Произвольный текст 2
[02:00.00]Произвольный текст 3
Выберите в "Балаболке" пункт главного меню Сервис|Преобразовать субтитры. В качестве синтезатора речи желательно использовать не старый голос "Николай", а что-то более новое, так как "Николай" не умеет вставлять паузы в звуковые файлы. Либо на вкладке "Настройки" укажите более свежий голос (не обязательно русский), который будет "читать" паузы между репликами.
Также, можно использовать онлайн-сервисы для преобразования LRC в звуковой файл: в "Балаболке" это пункт главного меню Сервис|Онлайн-сервис для синтеза речи. У "Яндекса" хорошие русские голоса, можно использовать этот сервис. На вкладке "Субтитры" выберите имя файла LRC, выберите голос и нажмите кнопку "Сохранить". (Надеюсь, соревнования длятся не много часов, так как результирующий звуковой файл может получится очень большим и на его создание уйдет много времени.)
- wasyaka
- V.I.P.
Скрипты для Demagog
С Наступившим!
Словарь *.dic
Сортировка: предлагаемая но не устраиваемая
А сделать СКРИПТОМ такую сортировку? По омографам?
С дополнением? в соответствующий каталог:
# омограф =
фраза с омографом
навроде словаря в hmg?
Примерно такой (сделано вручную и пополнение оч-чень нудное)
#автослесаря =
подмастерьем автослесаря=подмастерьем автослЕсаря
#адреса =
в честь адреса=в честь Адреса
*, адреса,=, адресА,
адреса ваши=адресА ваши
#аду =
увидеть аду=увидеть Аду
#ангары =
видишь, ангары=видишь, ангАры
#атласа =
жемчужно - белого атласа=жемчужно - белого атлАса
затёртого атласа=затёртого атлАса
Словарь *.dic
Сортировка: предлагаемая но не устраиваемая
А сделать СКРИПТОМ такую сортировку? По омографам?
С дополнением? в соответствующий каталог:
# омограф =
фраза с омографом
навроде словаря в hmg?
Примерно такой (сделано вручную и пополнение оч-чень нудное)
#автослесаря =
подмастерьем автослесаря=подмастерьем автослЕсаря
#адреса =
в честь адреса=в честь Адреса
*, адреса,=, адресА,
адреса ваши=адресА ваши
#аду =
увидеть аду=увидеть Аду
#ангары =
видишь, ангары=видишь, ангАры
#атласа =
жемчужно - белого атласа=жемчужно - белого атлАса
затёртого атласа=затёртого атлАса
- tonio_k
- V.I.P.
Скрипты для Demagog
Думаю можно, но с некоторыми особенностями...
Нужно скрипту объяснить какие слова считаются омографами. Тут мне представляется 2 варианта:
1) Для этого должен быть отдельный файл в котором будут перечислены все омографы. Например allomorphs.txt. Тогда любой новый словарь можно будет "отсортировать" по списку allomorphs.txt
2) можно непосредственно в самом словаре *.dic перечислять омографы добавляя знак решётки в качестве метки. При этом знак # как комментарий более в словаре применять нельзя что бы не было проблем при сортировке. Тогда скрипт сначала будет искать с словаре омографы помеченые знаком #, и составлять из найденного список allomorphs, затем по этому списку сортировать правила как в п.1
Минусы предлагаемой сортировки через скрипт:
1)Если какой либо омограф будет пропущен (не перечислен) самим пользователем при создании allomorphs.txt либо не перечислен в *.dic с пометкой #, то правила содержащие только этот омограф будут утеряны!
2) если в одном правиле присутствуют два омографа, то правило будет задвоено - продублировано и отсортировано для каждого омографа.
Из плюсов, в списке allomorphs или в словаре *.dic с пометкой # можно будет перечислять омографы в виде:
#замк*
#стрелк*
удобно что бы не перечислять все варианты однотипных омографов.
UPD
#замк* не удачная мысль. Сюда может быть продублировано правило
замкнутым кругом=замкнутым крУгом
Даже тут звёздочки надо использовать с умом.
Нужно скрипту объяснить какие слова считаются омографами. Тут мне представляется 2 варианта:
1) Для этого должен быть отдельный файл в котором будут перечислены все омографы. Например allomorphs.txt. Тогда любой новый словарь можно будет "отсортировать" по списку allomorphs.txt
2) можно непосредственно в самом словаре *.dic перечислять омографы добавляя знак решётки в качестве метки. При этом знак # как комментарий более в словаре применять нельзя что бы не было проблем при сортировке. Тогда скрипт сначала будет искать с словаре омографы помеченые знаком #, и составлять из найденного список allomorphs, затем по этому списку сортировать правила как в п.1
Минусы предлагаемой сортировки через скрипт:
1)Если какой либо омограф будет пропущен (не перечислен) самим пользователем при создании allomorphs.txt либо не перечислен в *.dic с пометкой #, то правила содержащие только этот омограф будут утеряны!
2) если в одном правиле присутствуют два омографа, то правило будет задвоено - продублировано и отсортировано для каждого омографа.
Из плюсов, в списке allomorphs или в словаре *.dic с пометкой # можно будет перечислять омографы в виде:
#замк*
#стрелк*
удобно что бы не перечислять все варианты однотипных омографов.
UPD
#замк* не удачная мысль. Сюда может быть продублировано правило
замкнутым кругом=замкнутым крУгом
Даже тут звёздочки надо использовать с умом.
- wasyaka
- V.I.P.
- flegont
- V.I.P.
Скрипты для Demagog
А если знак комментария для обозначения омографа применять в уникальной комбинации с каким-то другим символом (символами)? Тогда другие знаки "обычных комментариев" не помешают. Например:
#~!~передохнут
передохнут от жары= передохнУт от жары
#~!~передохнут
передохнут от жары= передохнУт от жары
- tonio_k
- V.I.P.
Скрипты для Demagog
Для словаря dic да и самому скрипту по сути без разницы какой символ или символы будут уникальные - главное что бы строки с омографами не содержали = или :: тем самым превращая слово в правило. Можно и так записать:
•передохнут
передохнут от жары= передохнУт от жары
Тогда знак # можно смело использовать в других местах словаря по его прямому назначению. А в скрипте прописать: символ "•" - считать маркером омографа.
От маркера требуется что бы он был удобен, нагляден (пожирнее на экране) ну и завести его можно было по быстрому. Тут # самое удобное. Можно и тройной ### записать.
Использование # - скорее дань традиции добавлять в словарь то, что не участвует в заменах dic комментировать символом решетка. Например "Индексный метод" применения rex словарей через скрипт применяет примерно тот же принцип при индексации. А при индексации символ # используется как метка индексных слов при составлении словаря. Единственное отличие от индексного метода, рассматриваю в сортировке, о которой просит wasyaka, использовать поиск правил содержащих омографы по Dic шаблону (через DicMatch). Это будет не очень быстрая сортировка из за поиска не по шаблону lua, зато реально можно будет записывать ключевые слова омографы со звездочками. Если окажется, что огромный словарь будет сортироваться ооочень долго, тогда можно будет и на сортировку по lua шаблону перейти.
- tonio_k
- V.I.P.
Скрипты для Demagog
В открытом в текущем окне словаре DIC скрипт распределяет правила по ключевым словам (омографам).
Строка с ключевым словом (омографом) должна начинаться со знака # (можно записать несколько: ###)
Распределение происходит по ключевым словам (омографам) без дублирования. Это означает, что если в правиле dic присутствуют 2 омографа, то данное правило перераспределится только к одному ключевому слову (омографу) - первому по алфавиту.
При распределении правила dic не сортируются.
Нераспределённые правила (к которым не нашлись ключевые слова) переносятся в начало словаря с пометкой ###Нераспределённые правила.
Ключевые слова можно записать в виде целого слова:
###стрелка
###стрелки
###стрелку
тогда к каждому ключевому слову распределятся соответствующие правила dic
Или можно записать в виде lua шаблона:
###стрелк[а-яё]+
###стрелк[аиу]
тогда правила dic распределяются согласно lua-шаблону
Пример работы со скриптом:
► Показать
- tonio_k
- V.I.P.
Скрипты для Demagog
скрипты lua пишутся под программу Демагог. Именно Демагог "понимает" и запускает скрипты. Так что научить стороннюю программу чему либо не получится, если она не поддерживает скрипты lua. Можно по-изголяться и попробовать сделать некий симбиоз двух программ Демагог и Booki. Это предполагает обязательный запуск Демагога, который при помощи скрипта lua будет что-то делать с файлами (копировать, перемещать,переименовать, удалять или сохранить fb2 в txt).
Скрипт lua в Демагоге, думаю, для этого можно сделать, вопрос в том, откуда будет браться текстовая информация: фамилия, имя, жанр? Что должно быть автоматизировано? И вообще, устроит ли вас схема одновременного запуска вашей программы и программы Демагог для решения эпизодических задач?KostyasaRgy писал(а): ↑22 янв 2021 06:48создавала соответствующую папку "Фимилия Имя" автора, а если еще и с вложенной папкой "жанр", так совсем было бы замечательно.
- wasyaka
- V.I.P.
Скрипты для Demagog
Для этого есть готовая прогаKostyasaRgy писал(а): ↑22 янв 2021 06:48соответствующую папку "Фимилия Имя" автора, а если еще и с вложенной папкой "жанр", так совсем было бы замечательно.
calibre: универсальное решение для ваших электронных книг
► Показать
- And1z
- Прохожий
Скрипты для Demagog
Подскажите плз, реально ли реализовать разбивку по главам озвученной книги?
Чтобы каждая глава была отдельным mp3 файлом. (для удобства делаю по главам, не удобно когда много глав и всё в ручную каждую главу вырезаю, хотелось бы както автоматизировать)
Например какое-то ключевое слово или символ для создание отдельного мп3... (сделать анлим по времени и по размеру файла, но когда встречается ключ-слово то чтобы создавало на выходе новый файл)
Чтобы каждая глава была отдельным mp3 файлом. (для удобства делаю по главам, не удобно когда много глав и всё в ручную каждую главу вырезаю, хотелось бы както автоматизировать)
Например какое-то ключевое слово или символ для создание отдельного мп3... (сделать анлим по времени и по размеру файла, но когда встречается ключ-слово то чтобы создавало на выходе новый файл)
- tonio_k
- V.I.P.
Скрипты для Demagog
попробуйте такой скрипт: данный скрипт текст в окне Демагога разбивает по главам и в указанной папке появляются текстовые файлы с отдельной главой в каждом файле.
Далее (если записываете в аудио штатно) применяем пакетную запись в аудио ко всем текстовым файлам (полученным при разбитии на главы) в папке. В настройках перед записью в аудио указываем максимальное количество символов в одном аудиофайле. В итоге получаем: одна глава = один mp3
- flegont
- V.I.P.
Скрипты для Demagog
О функции Form()
Начиная с вер. 397 макет формы ввода задается не в текстовом виде, а в виде таблицы Lua. Хотя и прежняя запись будет работать (но упоминание о ней из "Шпаргалки" исключено )
Записи очень похожи, но табличная гибче и позволяет вычислять элементы шаблона "на лету". Для сравнения:
А вот так теперь выглядит скрипт PlayYandex.lua из моей личной сборки
Еще пример. Конвертер аудиофайлов, на основе converter.lua, написанного ув. balaamster
Начиная с вер. 397 макет формы ввода задается не в текстовом виде, а в виде таблицы Lua. Хотя и прежняя запись будет работать (но упоминание о ней из "Шпаргалки" исключено )
Записи очень похожи, но табличная гибче и позволяет вычислять элементы шаблона "на лету". Для сравнения:
► Показать
► Показать
► Показать
- tonio_k
- V.I.P.
Скрипты для Demagog
не смог разобраться с функцией Execute()
Например у меня есть команды:
Может ли Execute() запустить эти команды вообще? А скрытом виде?
Например у меня есть команды:
Код: Выделить всё
os.execute(' mkdir "d:\temp\1\" ')--Создать каталог 1
os.execute(' RD /S /Q "d:\temp\1\" ')--удалить каталог 1 со всем содержимым
- flegont
- V.I.P.
Скрипты для Demagog
Функция Execute служит для запуска всяческих исполняемых файлов: *.exe, *.com, *.bat и т.п. (с параметрами или без). Поэтому создадим 2 исполняемых файла:
m.bat, содержащий текст:
и d.bat, содержащий текст:
Для их выполнения теперь можно применять функцию Execute
m.bat, содержащий текст:
Код: Выделить всё
mkdir "d:\temp\1\"
Код: Выделить всё
RD /S /Q "d:\temp\1\"
Код: Выделить всё
Execute('m.bat','',wsHide) -- создает папку 1
Execute('d.bat','',wsHide) -- удаляет папку 1 со всем содержимым
-- всё происходит скрытно от пользователя
- Lecron
- Специалист
- tonio_k
- V.I.P.
Скрипты для Demagog
flegont, у меня тут такое рационализаторское предложение. Взять на вооружение (в калькулятор) вот такую функцию:
Эта функция удаляет дубликаты в строках без сортировки. Функция полезна, когда имеем на руках таблицу состоящую из большого количества строк и из которой нужно удалить дубликаты, при этом сама сортировка не требуется. Сейчас же в калькуляторе удаление дубликатов делается только через функции "сортировка без дубликатов".
С учетом предложенной function unique(l) (название и переменные поменяйте на ваше усмотрение) предлагаю изменить function table.sortuniq(lines) на такой вариант:Тогда получается, если удаление дубликатов применить к строкам первым, то количество строк (при наличии дубликатов) уменьшится. И такая ресурсозатратная процедура как сортировка отработает быстрее.
Код: Выделить всё
-- lines without duplicates
function unique(a)
local q = {}
local t = {}
local k = 0
for i = 1, #a do
if q[a[i]] == nil then
k=k+1
q[a[i]] = ''
t[k] = a[i]
end
end
return t
end
► Показать
С учетом предложенной function unique(l) (название и переменные поменяйте на ваше усмотрение) предлагаю изменить function table.sortuniq(lines) на такой вариант:
Код: Выделить всё
function table.sortuniq(lines)
lines = unique(lines)
table.sort(lines)
return lines
end
- flegont
- V.I.P.
Скрипты для Demagog
Я согласен, что нынешняя реализация удаления дубликатов через сортировку - это очень плохая идея. Но предложенный вами метод удаления оных тоже пока вызывает сомнение. Проблема в обоих случаях в том, что работает это только для таблиц с числовой индексацией. Но не для ассоциативных таблиц. А хочется какого-то общего метода...
Код: Выделить всё
t = {}
t['один'] = 1
t['два'] = 2
t['три'] = 1
d = unique(t) -- удаляем дубликаты
print(t['три']) -- напрасно ждали, что теперь будет nil
- tonio_k
- V.I.P.
Скрипты для Demagog
а не получится тогда посудомоечный пылесос? Пока после посуды не просохнет пылесосить не станет. Я к тому, что такой комбаин может оказаться не таким быстрым как отдельно посудомойка и хлеборезка. Для конкретных задач - пусть будет конкретное решение?
- flegont
- V.I.P.
Скрипты для Demagog
Может всё же попробовать через for key, value in pairs(a) do ...
Будет ли это приемлемо по скорости? А там уже определиться, каким путем идти...
Будет ли это приемлемо по скорости? А там уже определиться, каким путем идти...
- flegont
- V.I.P.
Скрипты для Demagog
Хотя, да... начать лучше с простого. Пусть будет unique для выявления строк без дубликатов. А общий случай рассмотрим как-нибудь потом.
Как-то так:
Как-то так:
Код: Выделить всё
-- lines without duplicates
function unique(a)
local q, t = {}, {}
for i = 1, #a do
if not q[a[i]] then
q[a[i]] = true
t[#t+1] = a[i]
end
end
return t
end
- Lecron
- Специалист
Скрипты для Demagog
tonio_k, flegont, Зачем проверять значение? Разве хэш-таблицы автоматически не поддерживают уникальность ключей? Или есть принципиальная разница, какая из уникальных строк в нее попадут, первая или последняя?
а если номер строки вообще не важен
Код: Выделить всё
for i = 1, #a do
q[a[i]] = i
end
Код: Выделить всё
local set = {}
for _, l in ipairs(a) do set[l] = true end
return set
- tonio_k
- V.I.P.
Скрипты для Demagog
я тоже сначала думал в этом направлении. Но при всём отсутствии принципиальной разницы руководствовался 2 моментами:
1)
мне это не известно, поэтому предположил, что предложенный вами первый пример это по сути многократная "перезапись" ячейки. Что быстрее перезапись ячейки или 2 операции: проверка наличия ячейки и при ее отсутствии добавление новой ячейки? Я сделал предположение что быстрее последнее.поддерживают уникальность ключей?
2)
Сохранить общую структуру первоначального списка при удалении дубликатов может оказаться важным элементом. Например в ситуации удаления дубликатов в словаре dic чтобы сохранить его текущую пользовательскую сортировку.
- Lecron
- Специалист
Скрипты для Demagog
Ну вообще-то это суть всех хэш-таблиц. Иначе как дважды записать ячейку по одному ключу?
t['1'] = 1
t['1'] = 2
А если значения не нужны, получаем уникальное множество (set).
Ваш сложнее. Вы дважды хэшируете строку и проводите поиск в таблице. Добавление записи так же производит поиск и только в случае отсутсвия делает вставку. Более того — трижды, т.к. работаете с двумя таблицами.
она и не должна изменится. По крайне мере в известных мне скриптовых языках порядок соответствует созданию. Да и проверить не сложно.
Код: Выделить всё
t['один'] = true
t['два'] = true
t['один'] = true
- flegont
- V.I.P.
Скрипты для Demagog
Согласен, можно и не проверять значение.
и получаем набор уникальных ключей - дубликаты погасили друг друга. Осталось соорудить из них упорядоченную таблицу.
Работает в среднем на 20% быстрее, но (в отличие от варианта, предложенного ув. tonio_k) не сохраняет порядок строк. Он меняется при каждом выполнении скрипта.
Тест:
Результат одного из прогонов:
Как видим, действительно имеется выигрыш по времени. 0,016 секунды для таблицы из 5 миллионов строк.
Код: Выделить всё
for i = 1, #a do
q[a[i]] = true
end
Код: Выделить всё
function unique2(a)
local q, t = {}, {}
for i = 1, #a do
q[a[i]] = true
end
for key, value in pairs(q) do
t[#t+1] = key
end
return t
end
Тест:
Код: Выделить всё
-- lines without duplicates
function unique(a)
local q, t = {}, {}
for i = 1, #a do
if not q[a[i]] then
q[a[i]] = true
t[#t+1] = a[i]
end
end
return t
end
function unique2(a)
local q, t = {}, {}
for i = 1, #a do
q[a[i]] = true
end
for key, value in pairs(q) do
t[#t+1] = key
end
return t
end
-- Test
-- формируем большую тестовую таблицу, изобилующую дубликатами
t = {}
for i = 1,1000000 do
t[#t+1] = '1)х.ыфЁ:66;%%?**'
end
for i = 1,1000000 do
t[#t+1] = '2)двести двадцать два миллиона попугаев'
end
for i = 1,1000000 do
t[#t+1] = '3)берег пруда был покрыт выкарабкивающимися из воды лягушками'
end
for i = 1,1000000 do
t[#t+1] = '4)odnA:Fnp0]q39487`253455fmdlsk*$#^YT&(*_)(e gjgf ,skf cj,frf'
end
for i = 1,1000000 do
t[#t+1] = '5)Жил-был великий писатель, Лев Николаич Толстой, Не ел он ни рыбы ни мяса, ходил совершенно босой. Жена его - Софья Толстая, напротив, любила поесть. Она не ходила босая, спасая фамильную честь.'
end
z = os.clock()
d = unique(t)
time = os.clock()-z
print('\149 unicue. time= ',time)
for i = 1,#d do
print(d[i])
end
print()
z = os.clock()
d = unique2(t)
time = os.clock()-z
print('\149 unicue2. time= ',time)
for i = 1,#d do
print(d[i])
end
Код: Выделить всё
# Script>-- lines without duplicates2.txt
• unicue. time= 0.17199999999957
1)х.ыфЁ:66;%%?**
2)двести двадцать два миллиона попугаев
3)берег пруда был покрыт выкарабкивающимися из воды лягушками
4)odnA:Fnp0]q39487`253455fmdlsk*$#^YT&(*_)(e gjgf ,skf cj,frf
5)Жил-был великий писатель, Лев Николаич Толстой, Не ел он ни рыбы ни мяса, ходил совершенно босой. Жена его - Софья Толстая, напротив, любила поесть. Она не ходила босая, спасая фамильную честь.
• unicue2. time= 0.15599999999995
1)х.ыфЁ:66;%%?**
5)Жил-был великий писатель, Лев Николаич Толстой, Не ел он ни рыбы ни мяса, ходил совершенно босой. Жена его - Софья Толстая, напротив, любила поесть. Она не ходила босая, спасая фамильную честь.
2)двести двадцать два миллиона попугаев
4)odnA:Fnp0]q39487`253455fmdlsk*$#^YT&(*_)(e gjgf ,skf cj,frf
3)берег пруда был покрыт выкарабкивающимися из воды лягушками
- Lecron
- Специалист
Скрипты для Demagog
Зачем? Если неудобно читать ключи, просто пишите
Код: Выделить всё
for _, line in ipairs(a) do set[line] = line end
Тут надо смотреть внимательнее. Почему t[int] сохраняет порядок, а t[str] нет?
Все упирается в результат эксперимента
Код: Выделить всё
t['один'] = 'один'
t['два'] = 'два'
t['один'] = 'один'
Борюсь не за время, а за понятность кода.
Если повторное присваивание значения ключу таки меняет порядок следования, вторая таблица все равно не нужна. Просто не присваиваем повторно.
Код: Выделить всё
function unique(a)
local set = {}
for _, line in ipairs(a) do
if set[line] == nil then
set[line] = line
end
end
return set
end
- wasyaka
- V.I.P.
- flegont
- V.I.P.
Скрипты для Demagog
Заменяю в своем примере unique2 на вариант от ув. Lecron, и запускаю скрипт. Результат:
Код: Выделить всё
# Script>-- lines without duplicates2.txt
• unicue. time= 0.178
1)х.ыфЁ:66;%%?**
2)двести двадцать два миллиона попугаев
3)берег пруда был покрыт выкарабкивающимися из воды лягушками
4)odnA:Fnp0]q39487`253455fmdlsk*$#^YT&(*_)(e gjgf ,skf cj,frf
5)Жил-был великий писатель, Лев Николаич Толстой, Не ел он ни рыбы ни мяса, ходил совершенно босой. Жена его - Софья Толстая, напртив, любила поесть. Она не ходила босая, спасая фамильную честь.
• unicue2. time= 0.35999999999999
- Lecron
- Специалист
Скрипты для Demagog
Для меня lua сильно иностранный язык. Предполагаю наличие синтаксических ошибок в коде. Но я говорю про алгоритм, а не сам код. Зачем строки хранить в таблице с сурогатным числовым ключом, а флаги присутствия строк в таблице с текстовым?
И почему она возвращается, если все что я делаю
Код: Выделить всё
t[s] = s
На счет времени, отличие еще в способе иттерации, через индекс или по самим значениям. Вы лучше знаете язык, вам и карты в руки. Сами понимаете, работа с одной таблицей, не может быть больше чем с двумя.
- tonio_k
- V.I.P.
- flegont
- V.I.P.
Скрипты для Demagog
Ради полноты эксперимента, подсчитал для своего контрольного примера время сортировки (обычной алфавитной, как table.sort(t) ).
Для 5 млн строк время сортировки = 10.794 сек
А удаление дубликатов по времени = 0.175 сек
Разница более чем в 60 раз.
Т.о. проверка на дубликаты занимает ничтожное время, и если они действительно были в большом количестве, то их удаление заметно ускорит сортировку.
Для 5 млн строк время сортировки = 10.794 сек
А удаление дубликатов по времени = 0.175 сек
Разница более чем в 60 раз.
Т.о. проверка на дубликаты занимает ничтожное время, и если они действительно были в большом количестве, то их удаление заметно ускорит сортировку.
- wasyaka
- V.I.P.
Скрипты для Demagog
http://i91650e3.beget.tech/viewtopic.php?t=59&start=750
Сборка:
DemagogYandexUni.rar от ув. speeck
Словарь
11. 51_ОМОГРАФЫ_птр
Затрачено буквально пара минут
Итог
Словарь очищенный от "неомографов" в сортировке по Омографам и по алфавиту в пределах омографа (дубликаты не обнаружены)
(При желании в любой сортировке) И сами "неомографы" С учётом того, что это редко - довольно редко - применяемая функция - зачем заморачиваться?
А вот функция добавить в словарь которая сразу бы отсекала всё непотребное - была бы очень полезна.
- tonio_k
- V.I.P.
Скрипты для Demagog
Захотел сделать функцию сканирование папки со всеми подкаталогами и получение списка путей ко всем файлам по маске. Но почему-то у меня одна строчка отказывается работать.
Черновик функции:
Пример использования:
Пример рабочий в плане: в функции строка без ремарки print список путей выводит (причем, список вместе с папками)
Но если я хочу проверить является ли указанный путь именно к файлу а не к папке, то ставим ремарку к print и пробуем разремарить FileExists - так уже вообще ничего не выводит. Ощущение, что FileExists не понимает предлагаемый путь либо где то у меня ошибка.
Черновик функции:
Код: Выделить всё
function DirFolder(f,m)
local s = io.popen('dir '..f..m..' /B /S /O:S', 'r' )
s = s:read "*a"
s = DosToAnsi(s)
s = string.split(s,'\r')-- таблицу
GaugeInit(#s)
for i=1,#s do
Gauge(i)
--if FileExists(s[i]) then print(s[i]) end
print(s[i])
end
Gauge(0)
s = table.concat(s,'\r') -- в текст
s = string.gsub(s,'[\r\n]+','\r')
return(s)
end
Код: Выделить всё
f='D:\\tmp\\Книги\\'
m = '*.txt'--маска
DirFolder(f,m)
Но если я хочу проверить является ли указанный путь именно к файлу а не к папке, то ставим ремарку к print и пробуем разремарить FileExists - так уже вообще ничего не выводит. Ощущение, что FileExists не понимает предлагаемый путь либо где то у меня ошибка.
- Lecron
- Специалист
Скрипты для Demagog
tonio_k, Желательно публиковать еще и вывод (часть вывода) успешного варианта.
В таких случаях, начинаю с print(FileExists(s)), а потом играть с входным параметром. Если исключить существование ошибок в FileExists, можете накосячить только в излишнем преобразовании DosToAnsi.
Но может проще исключить каталоги сразу dir /A-D ?
В таких случаях, начинаю с print(FileExists(s)), а потом играть с входным параметром. Если исключить существование ошибок в FileExists, можете накосячить только в излишнем преобразовании DosToAnsi.
Но может проще исключить каталоги сразу dir /A-D ?
- flegont
- V.I.P.
Скрипты для Demagog
FileExists(f)- возвращает true, если файл с именем f существует; и false в противном случае
Exists(f) - существует ли файл или папка f; возвращает true / false и код ошибки
IsFolder(f) - существует ли папка f; возвращает true / false
Exists(f) - существует ли файл или папка f; возвращает true / false и код ошибки
IsFolder(f) - существует ли папка f; возвращает true / false
- tonio_k
- V.I.P.
Скрипты для Demagog
Нашел ошибку.
DOS выводит текст с символом-разделителем строк '\n'. А я по привычке пытаюсь сделать таблицу с символом-разделителем строк '\r'. В результате вместо списка получаю все пути в одну сплошную строку. Поправил так:
Пример для тестирования:
DOS выводит текст с символом-разделителем строк '\n'. А я по привычке пытаюсь сделать таблицу с символом-разделителем строк '\r'. В результате вместо списка получаю все пути в одну сплошную строку. Поправил так:
Код: Выделить всё
--вывести содержимое указанной папки вместе с подкаталогами.
--полученный cписок будет отсортирован по размеру файлов (по возрастанию)
function DirFolder(f,m)
local s = io.popen('dir '..f..m..' /B /S /O:S', 'r' )
s = s:read "*a"
s = DosToAnsi(s)
s = string.gsub(s,'[\r\n]+','\r') -- заменяю все варианты разделителей на '\r'
s = string.split(s,'\r')
local t={}
local u=0
for i=1,#s do
if FileExists(s[i]) then
u=u+1
t[u]=s[i]
end
end
s=nil
return(t)
end
Код: Выделить всё
f='D:\\tmp\\Книги\\'-- путь к папке
m = '*.*'-- маска файла "*.*" "*.fb2" "*00*.txt"
s=DirFolder(f,m)
for i=1, #s do
print(s[i])
end
- Lecron
- Специалист
Скрипты для Demagog
tonio_k, Глядя на ужасно нелогичный набор функций Exists, FileExists, IsFolder, хочу предостеречь от аналогичной ошибки. Делайте две функции DirItems(path, recursive) и DirFiles(path, mask, recursive), когда вторая будет вызывать первую и только фильтровать ее вывод. В идеале, маску вообще надо фильтровать отдельно, по месту приемения. Но в данном случае кмк это избыточно, таки не файловую библиотеку пишем.
- Lecron
- Специалист
Скрипты для Demagog
А сразу s = string.split(s,'\r\n') язык умеет? Нам здесь универсальность не нужна. Прграмма не кроссплатформенна и работатет только с выводом функции dir.
- tonio_k
- V.I.P.
Скрипты для Demagog
а что в них не так? очень удобные в использовании и понимании. В своих скриптах активно применяю.
а моя ошибка с этими функциями вообще никак не связана. Проблема в разбитии текста полученного от DOS команды dir (ну забыл я что DOS и блокнот любят разделитель '\n). Почему вообще полез в DOS? Потому что AllFiles(folder, mask) получает список файлов только из конкретной папки, а мне нужно было получить со всеми подкаталогами, причем отсортированный по размеру файлов в порядке убывания. Команда dir может одним махом такой список получить, причем сразу отсортированный по возрастанию размеров файлов. "отзеркалить" список, что бы сортировка с "по возрастанию" стало "в порядке убывания" - это уже не проблема.
умеет, но я же не программист что бы тонкости знать. А если текст корявый и разделитель в нем '\n\r' будет, тогда s = string.split(s,'\r\n') сработает? Или порядок символов не важен?
- Lecron
- Специалист
Скрипты для Demagog
Не так с организацией. Нарушение принципа единственной ответсвенности и единого наименования. Exists должна проверять существование файлового объекта, а IsFile и IsFolder только принадлежность к типу.
Дело не в ошибке. Есть такое понятие как инкапсуляция (гугл в помощь))). Вы заворачиваете io.popen и трансформацию вывода в функцию... и больше никогда об этом не думаете. В остальных местах работая уже с готовым списком путей.
После обсуждения обработки многих миллионов строк, обращать на это внимание, себя не уважать. Для интерпретатора, любые существующие объемы вывода dir, это ничто.
А я думал, что это простая логика))) Я тоже lua не знаю. Даже меньше вашего.
Порядок символов важен. Только измениться он не может. Функция dir как выводила данные 20 лет назад, так и через 20 будет выводить.
- flegont
- V.I.P.
Скрипты для Demagog
string.split - не входит в состав Lua. Это - самоделка, найденая в Инете. Так же, как вышеперечисленные FileExists, Exists, IsFolder. Я стараюсь не изобретать велосипеды сверх необходимости - почти все они уже изобретены. Если что-то пригодилось - используем, не оправдало ожиданий - выбросим.
А работает string.split очень интересно. Каждый символ, перечисленный во втором параметре, будет воспринят, как самостоятельный разделитель.
Результат:
a
bra
ka
da
bra
А работает string.split очень интересно. Каждый символ, перечисленный во втором параметре, будет воспринят, как самостоятельный разделитель.
Код: Выделить всё
s = 'a1bra2ka3da4bra'
a = string.split(s,'1234')
for i = 1,#a do
print(a[i])
end
a
bra
ka
da
bra
- flegont
- V.I.P.
Скрипты для Demagog
P.S. А что касается абстракции, наследования, инкапсуляции и полиморфизма, то (извиняюсь за оффтоп), как показала жизнь ООП - это катастрофа на триллион долларов
- tonio_k
- V.I.P.
Скрипты для Demagog
более того, получается что разделитель '1234' это аналогично выражению [1234]+ (с плюсиком) в регулярках. Буду иметь в виду. С такой трактовкой буду смелее использовать (и более широко применять) эту функцию
Код: Выделить всё
s = 'a1bra2ka3da4bra3113131sim444536031'
a = string.split(s,'1234')
for i = 1,#a do
print(a[i])
end
a
bra
ka
da
bra
sim
5
60
- Lecron
- Специалист
Скрипты для Demagog
В-первых, любая крайность — катастрофа. Во-вторых — прошу прощения, не совсем верно выразился. Скорее переиспользование, как капсуляция сложности.
Нужно ли оно? Если dir еще используется или предполагается использовать хоть где-то, то нужно. Нет — значит нет.
- tonio_k
- V.I.P.
Скрипты для Demagog
Пример получение контрольной суммы файла (хэш-суммы)
скрипт использует встроенную в Windows Certutil.exe
Код: Выделить всё
a=OpenDialog(true)
if a==nil then goto HALT end
item={'MD2','MD4','MD5','SHA1','SHA256','SHA384','SHA512',}
shapka = " Выберите криптографический хеш:"
dial = Menu(shapka,item,4)
if dial == 0 then goto HALT end
for i=1, #a do
local s = io.popen('certutil -hashfile "'..a[i]..'" '..item[dial], 'r' )
s = s:read "*a"
s = string.split(s,'\r\n')
s[2] = string.gsub(s[2],' ','')--удалить пробелы
print(s[2])
print(a[i])
print()
end
::HALT::
- flegont
- V.I.P.
- юрабойко
- Обыватель
Скрипты для Demagog
Мне нужен скрипт для автоматически расставить коммы после каждого слова или через одно, кроме коротких - не более 3 или 5 букв?
Если комма, это запятая, то во-первых так и пишите, а во-вторых любая из программ на форуме, поддерживающая rex словари это умеет.
\b\w{5,}(?=\s)=$0,
Шаблон начинающийся с начала слова, содержащий не менее 5 букв и не заканчивающийся пробелом (чтобы не зацепить знаки препинания), заменить на шаблон+запятая. Для "через одно" — \b\w+\s\w{5,}. Может какие-то нюансы не учел, но принцип такой, регулярки для этого и созданы. Если словарь не распознается из-за второго знака равно, заменить этот блок на негативный (?![\.\!\?,:])
Желательно подобный пример дайте, программу для редактирования файлов если надо тоже просьба напомнить.
Если комма, это запятая, то во-первых так и пишите, а во-вторых любая из программ на форуме, поддерживающая rex словари это умеет.
\b\w{5,}(?=\s)=$0,
Шаблон начинающийся с начала слова, содержащий не менее 5 букв и не заканчивающийся пробелом (чтобы не зацепить знаки препинания), заменить на шаблон+запятая. Для "через одно" — \b\w+\s\w{5,}. Может какие-то нюансы не учел, но принцип такой, регулярки для этого и созданы. Если словарь не распознается из-за второго знака равно, заменить этот блок на негативный (?![\.\!\?,:])
Желательно подобный пример дайте, программу для редактирования файлов если надо тоже просьба напомнить.
- юрабойко
- Обыватель
Скрипты для Demagog
Еще одна деталь - я уже пробовал заменить все знаки препинания на пробелы или запятые, потом командой найти заменить убрал все лишние пробелы, потом заменил все пробелы на это:
пробеле + запятая + пробел.
Результат прослушивания после этого в балаболке мне целом понравился, но коробит дискомфорт от длинной паузы после каждого слоова из одной буквы, но скорее всего так будет со всеми словати из пяти букв, и почти с гарантией - из трех букв.
пробеле + запятая + пробел.
Результат прослушивания после этого в балаболке мне целом понравился, но коробит дискомфорт от длинной паузы после каждого слоова из одной буквы, но скорее всего так будет со всеми словати из пяти букв, и почти с гарантией - из трех букв.