вторник, 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



воскресенье, 8 июля 2012 г.

mp4 и linux

Столкнулся с проблемой при воспроизведении mp4 файлов под linux. Даже всеядный VLC выдал ошибку такого содержания:


Не найден подходящий модуль декодирования:
VLC не поддерживает аудио или видео формат "mp4a". К сожалению, вы не можете это исправить.



После недолгих поисков в гугле и раздумий нашел простой способ борьбы с этим непотребством - установил пакет mplayer-vaapi. Тот же gstreamer-faad по отзывам справляется не хуже, но в репах я его не нашел. Такие дела.

суббота, 2 июня 2012 г.

Headset

Приобрел себе наконец-то нормальную Bluetooth-гарнитуру - rapoo h6060 headset. Сразу же заразил несколько приятелей идеей приобрести такую же.
Ну а чего, удобно, не привязан больше к компу, делаешь любые дела и одновременно слушаешь музыку или говоришь по скайпу. Дальность действия - до 10 м, но по опыту использования могу сказать что это справедливо при отсутствии на пути сигнала стен или других громоздких препятствий. Стоит зайти немного за угол и сигнал уже начинает звучать прерывисто. Кнопочки вполне удобны, микрофон встроен и совсем не выступает. Обошлась мне эта игрушка примерно в 1,5 килорубля. Что еще приятно, работы аккумулятора хватает на 16-20 часов, и перезаряжать не приходится сильно много.
Что касаемо софта, то тут возможны подводные камни. Драйверов с ними никаких не идет, да они и не нужны. Под windows с ними отлично работает BlueSoleil 6-8 версии. Только программа платная, и без активации не позволяет передать больше 2 Мб данных, что печально (Если кто знает другие рабочие варианты - отпишитесь). Еще неплохим вариантом является использование драйверов от WIDCOMM - на XP встало идеально.
 Под linux пришлось установить blueman, так как kde-шный KBluetooth не справился. Несмотря на то что он основан на GTK+, под кедами работает хорошо (нужно только запустить /usr/bin/blueman-manager.py). При поиске нужно зажать кнопку включения секунд на 5 и держать пока устройство не опознается. Дальше выбираем устройство в PulseAudio и дело в шляпе. В общем я доволен =\