пятница, 15 июня 2018 г.

Создание exe из Python 3.6 под Windows 10

    Для тех, кто программирует на Python, данный вопрос может оказаться актуальным, если нужно создать исполняемый файл, который сможет запустить обычный пользователь, не искушенный в программировании на этом языке, чтобы решить какую-то прикладную задачу. Для этого я сделал следующее (на примере скрипта tgproxy.py):
  1. Установил PyInstaller через pip install pyinstaller. После выполнения этой команды в папке с pip.exe появляются дополнительные скрипты и файлы.
  2. Задал каталог, в котором будет производиться поиск дополнительных модулей, импортируемых в скрипте:
    pyi-makespec --paths=C:\Users\Asus\AppData\Local\Programs\Python\Python36-32\Lib\site-packages tgproxy.py
  3. Запустил сборку командой pyinstaller tgproxy.py

    В папке dist\tgproxy следующая картина:

    В принципе, tgproxy.exe уже можно запускать из этой папки, но можно упаковать все зависимости в 1 файл. Для этого команда должна быть такого вида: pyinstaller --onefile tgproxy.py

    Ссылка на официальную документацию.

суббота, 17 августа 2013 г.

Испанская клавиатура в windows.

    Для тех, кто начал изучать испанский язык, либо тех, кто им пользуется для переписки/работы, нужна возможность ввода особых символов, среди которых есть как гласные с акцентом (á, é, í , ó, ú),  так и другие специфические (ü, ñ, ¡, ¿, Ñ). Нетрудно увидеть, что подавляющее большинство элементов испанского алфавита сходно с элементами английского. Поэтому я написал небольшую утилиту, эмулирующую испанскую раскладку.
    Почему бы не воспользоваться системной? У этого подхода, с моей точки зрения, есть несколько недостатков.
    Во-первых, не все умеют устанавливать раскладки, и для человека, не очень знакомого с компьютерами, это довольно непростая задача. Во-вторых, если компьютеров, за которыми приходится работать, много, то просто нет желания на каждом из них добавлять раскладку. В-третьих (и для меня это главная причина), просто неудобно постоянно переключаться между тремя раскладками (русской, английской и испанской), а это приходится делать довольно часто. В моём же случае, достаточно просто закрыть утилиту двумя кликами мыши и раскладки по-прежнему будет две. 
     Принцип работы прост, утилита запускается двойным кликом мыши и в системном трее (рядом с часами) появляется её значок, который имеет контекстное меню (которое можно вызвать по правому клику мышью на значке). Через это меню программа и закрывается.


    Принцип набора схож с раскладкой в системной Windows. Основная часть клавиш не отличается от английской раскладки, для того, чтобы ввести гласную с акцентом сначала нажимаем без удерживания ' (в русской версии э) и потом гласную.
 ' + a = á
 ' + e = é
 ' + u = ú
 ' + o = ó
 ' + i = í
    Заглавные буквы вводятся по такому же принципу, то есть к примеру, чтобы набрать Á, сначала нажимаем апостроф, потом SHIFT+A:  ' + A = Á.

    С другими символами интереснее, дело в том, что в английской и испанской раскладках ввод некоторых знаков пунктуации различается, например, в испанской обычный вопросительный знак вводится комбинацией Shift + "=", а в английской Shift+"?". Поскольку привык я к английской раскладке, то решил оставить минимум изменений, поэтому лишь символы ü, ñ, ¡, ¿, Ñ вводятся немного иначе. Символ ñ соответствует ";" или "ж", Ñ - комбинации Ctrl+";" (Ctrl + "ж"), ¡ - Ctrl + "-", ¿ - Ctrl + "=", ü - Ctrl + u. Символ же точки с запятой можно набрать комбинацией Ctrl + 0. Отмечу, что здесь Ctrl удерживается перед нажатием последующей клавиши.
ñ = ;
Ñ = Ctrl + ;
¡ = Ctrl + "-",
¿ = Ctrl + "="
ü = Ctrl + "u"

    Лично для меня такая система оказалась гораздо удобнее, чем стандартная раскладка.
    Для тех, кому это интересно, написана утилита на скриптовом AutoIt, установки никакой не требуется, поскольку интерпретатор встроен в исполняемый файл. Проверено в Windows XP и Windows 7 Professional.

вторник, 2 июля 2013 г.

Подсчёт количества строк кода

Такая потребность может возникнуть не только при создании и для поддержания собственного проекта, но и для анализа уже существующих. Чтобы оценить эффективность проведенной оптимизации, вести статистику собственной производительности, или чтобы оценить трудозатраты. Разумеется, оценивать таким образом эффективность и функциональность кода, а значит и труд программиста в общем нельзя, один и тот же фрагмент кода можно написать и короче, и длиннее. А вот, к примеру, сравнивать уязвимость программного продукта косвенным образом уже можно (чем меньше кода имеет проект, тем меньше потенциальных ошибок в нём содержится). В общем, задача данного аспекта метрики ПО зачастую возникает.

Как известно, помимо пустых и непустых строк, следует разделять физические строки кода и логические (первые могут быть комментарием, вторые отражают количество операторов). Для этой задачи хорошо подходит утилита cloc ("Cout lines of code"), которую кстати можно найти и в портах FreeBSD. Комментарии не учитываются, как и пустые строки, имеется возможность не учитывать копии файлов. Утилита умеет обрабатывать файлы, директории и архивы. Установки никакой не требует и состоит из одного файла, поддерживает большое количество систем и языков. Конкретно под Windows использование заключается в запуске утилиты из командной строки с определенными параметрами.

На примере моего рабочего проекта (программа для мониторинга и прослушивания icecast радиостанций на C#), получилось следующее:

c:\Users\admin\Downloads>cloc-1.58.exe "C:\Users\admin\Docu
ments\Visual Studio 2010\Projects\RegionsMonitoring\RegionsMonitoring"
      28 text files.
      25 unique files.
      24 files ignored.

http://cloc.sourceforge.net v 1.58  T=1.0 s (13.0 files/s, 17430.0 lines/s)
-------------------------------------------------------------------------------
Language                     files          blank        comment           code
-------------------------------------------------------------------------------
XML                              2             15              0          13979
C#                              10            148            436           2741
MSBuild scripts                  1              0              7            104
-------------------------------------------------------------------------------
SUM:                            13            163            443          16824
-------------------------------------------------------------------------------


Можно обрабатывать только файлы с определённым расширением:

c:\Users\admin\Downloads>cloc-1.58.exe --match-f="\.cs$" "C:\Users\admin\Documen
ts\Visual Studio 2010\Projects\RegionsMonitoring\RegionsMonitoring"
      10 text files.
      10 unique files.
       0 files ignored.

http://cloc.sourceforge.net v 1.58  T=0.5 s (20.0 files/s, 6650.0 lines/s)
-------------------------------------------------------------------------------
Language                     files          blank        comment           code
-------------------------------------------------------------------------------
C#                              10            148            436           2741
-------------------------------------------------------------------------------
SUM:                            10            148            436           2741
-------------------------------------------------------------------------------

Здесь, разумеется, часть кода является сгенерированной самой IDE, для более точного анализа можно исключить из анализа Program.cs:
c:\Users\admin\Downloads>cloc-1.58.exe --match-f="\.cs$" --not-match-f="Program"
 "C:\Users\admin\Documents\Visual Studio 2010\Projects\RegionsMonitoring\Regions
Monitoring"
       9 text files.
       9 unique files.
       0 files ignored.

http://cloc.sourceforge.net v 1.58  T=0.5 s (18.0 files/s, 6606.0 lines/s)
-------------------------------------------------------------------------------
Language                     files          blank        comment           code
-------------------------------------------------------------------------------
C#                               9            147            433           2723
-------------------------------------------------------------------------------
SUM:                             9            147            433           2723
-------------------------------------------------------------------------------

Вот таким образом можно приблизительно оценить объём кода, или выполнить какие-то более сложные манипуляции (обрезать все комментарии, сравнить две версии одного и того же исходника и т.д.)

суббота, 20 апреля 2013 г.

Испанские субтитры и юникод




Для тех, кто изучает испанский язык по фильмам и сериалам, наверное знакома ситуация, когда субтитры доступны в формате ANSI, при этом на системе с русским языком они отображаются некорректно:


Попробовал найти штатный перекодировщик в SubtitleWorkshop и еще нескольких подобных программах, но в итоге решил перевести в нормальный вид самостоятельно, используя только Python. В итоге все прилично:



Собственно, код:

# -*- coding: utf-8 -*-
import os
import codecs
import re

path = os.getcwd()
dirs = os.listdir(path)

srclist = ['ї','б','н','й','Ў','у','ъ']
replist = ['¿','á','í','é','¡','ó','ú']
repldict = dict(zip(srclist,replist))

map(lambda x: unicode(x,'utf-8').encode('utf-8'), replist)

for sfile in dirs:
    if not '.srt' in sfile:
        continue
    with codecs.open(sfile, 'r', 'windows-1251') as f:
        newarray = []
        for line in f:
            newline = line.encode('utf-8')
            for sym in srclist:
                sym = sym.decode('utf-8').encode('utf-8')
                if sym in line.encode('utf-8'):
                    newline = re.sub(sym,replist[srclist.index(sym)].decode('utf-8').encode('utf-8'),newline)
            newarray.append(newline.decode('utf-8'))
        f.close()
    with codecs.open(sfile + '.srt', 'w', 'utf-8') as l:
        l.writelines(newarray)
        l.close()

raw_input("Press Enter to exit"
            
В список srclist добавляются все литералы, требующие замены, а в replist соответствующие им заменяющие литералы. Скрипт ищет в текущей с ним директории все файлы *.srt и обрабатывает их, потом создает новый файл рядом со старым в формате UTF-8. Вот такой велосипед.

вторник, 5 февраля 2013 г.

Обнаружение утечек памяти в Visual C++


На днях обнаружил очень простой и полезный инструмент для обнаружения утечек памяти под windows. Для тех кто работает в Visual Studio будет весьма полезно. Называется система Visual Leak Detector for Visual C++ 2008/2010/2012. Взять можно здесь. Установка простая, после распаковки нужно добавить в студию пути к include и lib директориям софтины. 


После чего в самом исходнике в любом файле (кроме предварительно скомпилированного stdafx.h) нужно сделать инклуд #include <vld.h> и готово. Компилируем debug версию программы, запускаем на отладку и по завершении сеанса отладки прямо в консоли вывода будет примерно следующая информация:



Как видно здесь приводится полный стек вызовов для обнаруженной утечки.


среда, 17 октября 2012 г.

Компрессор фоток

Нашел в глубинах диска программку которую писал еще студентом для себя, еще на старом билдере, и решил поделиться, может кому пригодится. Идея очень простая, после поездки на море у меня скопилось на цифровике много фотографий в формате JPEG с большим размером (от 2 до 3-4 Мб). Программка позволяет сжать их без видимой потери качества. Установки конечно не требует. Доступно сжатие файлов директориями и папками, можно задавать соотношение степени сжатия/качества. Файлы меньше 1 Мб можно исключить из обработки установкой соответствующей галочки. Конечно, есть множество других способов сделать то же самое, но этот лично для меня удобен и я пользуюсь им периодически до сих пор.

Скачать

суббота, 1 сентября 2012 г.

Небольшая автоматизация Lotus Notes

На работе у меня в качестве системы документооборота используется связка Lotus Domino+Notes, написанная на Java. В основном мне приходится пользоваться ее почтовым клиентом. И возникла потребность автоматизировать довольно рутинную операцию, заключающуюся в том чтобы из последних пришедших от рекламного агентства писем копировать в рабочий каталог почтовые вложения.

Для решения этой задачи программным путем я решил использовать Lotus Script. Это BASIC-подобный язык, довольно хорошо документированный. После недолгого изучения документации я создал простой Агент (Создание - Агент) и задал ему такие параметры:

Собственно, код:
Sub Initialize
Dim session As NotesSession 'определяем среду текущего скрипта, обеспечивающую доступ к переменным окружения и различной информации
Dim db As NotesDatabase 'определяем базу данных Notes
Dim dc2 As NotesDocumentCollection 'определяем коллекцию документов из базы данных, выбранных с определенным критерием
Dim doc2 As NotesDocument 'определяем документ в базе данных
Dim body As NotesRichTextItem 'определяем объект форматированного RTF текста (тело письма)
Dim rtnav As NotesRichTextNavigator 'определяем объект навигатора по RTF содержимому
Dim att As NotesEmbeddedObject 'определяем встроенный объект для аттачмента
Set session = New NotesSession 'получаем доступ к текущей сессии (поскольку для одного скрипта возможна только одна сессия)
Set db = session.CurrentDatabase 'текущая база данных
REM Ищем все документы со словами тнт, нтв, монтаж, полоса за сегодняшнюю дату
Dim searchFor As String
Dim createDate As Variant
Dim nowDate As Variant
nowDate = Day(Now)
searchFor = "тнт"
Set dc2 = db.FTSearch(searchFor, 0) 'поиск по ключевой фразе среди всех документов
If dc2.count > 0 Then
Call ProcessFoundedDocs(dc2)
End If
searchFor = "нтв"
Set dc2 = db.FTSearch(searchFor, 0) 'поиск по ключевой фразе среди всех документов
If dc2.count > 0 Then
Call ProcessFoundedDocs(dc2)
End If
searchFor = "монтаж"
Set dc2 = db.FTSearch(searchFor, 0) 'поиск по ключевой фразе среди всех документов
If dc2.count > 0 Then
Call ProcessFoundedDocs(dc2)
End If
searchFor = "Полоса"
Set dc2 = db.FTSearch(searchFor, 0) 'поиск по ключевой фразе среди всех документов
If dc2.count > 0 Then
Call ProcessFoundedDocs(dc2)
End If
End Sub

Sub ProcessFoundedDocs(dc2 As notesDocumentCollection)
REM перебираем циклом найденные документы
Dim x As Integer
Dim filepath As String
For x% = 1 To dc2.count
Set doc2 = dc2.GetNthDocument(x%) 'берем N-й документ из коллекции
createDate = Day(doc2.Created) 'получаем дату его создания
If nowDate = createDate Then 'если документ сегодняшний
If doc2.HasEmbedded Then 'если документ имеет вложение
Set body = doc2.GetFirstItem("Body") 'тело документа
Set rtnav = body.CreateNavigator 'создаем объект навигатора по RTF содержимому
REM Получаем вложения
Set att = rtnav.GetFirstElement(RTELEM_TYPE_FILEATTACHMENT) 'первое вложение
filepath$ = "C:\Files\" & att.Source 'определяем куда копировать
Call att.ExtractFile("F:\POLOSA__NEW__\polosa__9\polosa_rtf" & att.Source) 'копируем
Do 
Set att = rtnav.GetElement
filepath$ = "F:\POLOSA__NEW__\polosa__9\polosa_rtf" & att.Source 'определяем куда копировать
Call att.ExtractFile(filepath$) 'копируем
Loop While rtnav.FindNextElement(RTELEM_TYPE_FILEATTACHMENT)
End If
End If
Next
End Sub