Обговорення користувача:Дядько Ігор/Прохання оновити статистику! (20.10.2011 - 25.10.2011)

Найсвіжіший коментар: Дядько Ігор 12 років тому

Обговорення користувача:Дядько Ігор/Прохання оновити статистику! (20.10.2011 - 25.10.2011)

Доброго вечора, шановний Дядьку Ігоре! Велике прохання оновити статистику із топ1000. БО! Іде тиждень і вона МАЄ оновлюватися щоденно! Якщо питання в часі, то розкажіть як, я сам буду оновлювати.... З повагою, --Nickispeaki 19:47, 20 жовтня 2011 (UTC)Відповісти

Дякую за оновлення! ;-) --Nickispeaki 23:26, 20 жовтня 2011 (UTC)Відповісти
То ми вже італійців обігнали і вийшли на 7 місце? --Nickispeaki 23:26, 20 жовтня 2011 (UTC)Відповісти
Можливо. Офіційний підрахунок раз у місяць. Можна, мабуть, наступного разу замінити російську на італійську. --Дядько Ігор 21:55, 21 жовтня 2011 (UTC)Відповісти
Питання в тому ЯК її оновлювати (статистику). Я б сам оновлював. Швидкість інету у мене добра. Щоправда, останні 2 місяці не регулярно буваю в інеті... То як оновлювати? Буду вдячний за детальну інструкцію. (пс. Останнім часом народ чомусь у мене пише на основній сторінці. Але ж для цього є сторінка Обговорення користувача? ;-0 ). --Nickispeaki 08:39, 25 жовтня 2011 (UTC)Відповісти
Інструкція.

1. Переконатися, що маєте python або встановити його.

2. Встановити і сконфігурувати pywikipedia.


3. Наступний скрип зберегти як getList1000.py в директорії pywikipedia

# -*- coding: utf-8 -*-
 
import sys
sys.path.append('..\..\PyWikipediaBot')
 
import wikipedia
 
article_name = 'List of articles every Wikipedia should have'
 
meta_wiki = wikipedia.Site('meta', 'meta')
meta_page = wikipedia.Page(meta_wiki, article_name)
article   = meta_page.get(get_redirect=False)
 
f = open('list.txt', 'w')
count = 0
grand_total = 0
 
name_last  = 0
name_first = article.find(u'[[en:', name_last)
while name_first > -1:
    name_mid  = article.find(u'|',  name_first)
 
 
    cat_start =article.rfind(u'\n== ', name_last, name_first)
    if cat_start > -1:
        cat_end   = article.find(u'==',cat_start+3, name_first)
        if cat_end > -1: 
            cat   = article[cat_start+3:cat_end]
            print
            print cat
            print ''.center(len(cat),'-')
            count = 0
 
    name_last = article.find(u']]', name_first)
    if name_last > name_mid:
      name_last = name_mid
    article_item = article[name_first+5:name_last]
    f.write((u'[[en:' + article_item + u']]').encode("utf_8"))
    f.write('\n')
    count += 1
    grand_total += 1
    print count, article_item
    name_first = article.find(u'[[en:', name_last)
 
f.close()
 
print ''
print 'GRAND TOTAL'
print '-----------'
print  grand_total, 'articles'


4. Наступний скрипт скопіювати й зберегти як stats.py в директорії pywikipedia

# -*- coding: utf-8 -*-
import sys
 
sys.path.append('..\..\PyWikipediaBot')
 
import pagegenerators
import wikipedia
import datetime
import re
 
#configuration
preloadNumber    = 125
languageWeights  = {'uk':1.3, 'en':1.0, 'ru':1.4, 'it':1.1}
languages        = ['uk', 'en', 'ru', 'it']
languageNames    = { 'uk':u'Українська', 'en':u'Англійська', 'ru':u'Російська', 'it':u'Італійська'}
localLanguage    = 'uk'
outputPage      = u'Вікіпедія:Статті, які повинні бути в усіх вікіпедіях/stat'
 
class Translations():
    def __init__(self, pages = [], languages=None):
        if languages is None:
            languages = [page.site().language() for page in pages]
 
        # remove duplicates
        uniqueLanguages = {}
        self.languages = [uniqueLanguages.setdefault(l,l) for l in languages if l not in uniqueLanguages]
 
        self.pages = {}
        for page in pages:
            self.addPage(page)
 
    def __iter__(self):
        for language in self.languages:
            yield self.getPage(language)
 
    def addPage(self, page):
        language = page.site().language()
        if language in self.languages:
            self.pages[language] = page
 
    def getPage(self, language):
        return self.pages[language] if language in self.pages else None
 
 
class TranslationsList():
    def __init__(self, pages, languages=None, preloadNumber = 125):
        self.preloadNumber = preloadNumber
 
        for page in pages:
            self.removeSection(page)
 
        if languages is None:
            languages = [page.site().language() for page in pages]
 
        # remove duplicates
        uniqueLanguages = {}
        self.languages = [uniqueLanguages.setdefault(l,l) for l in languages if l not in uniqueLanguages]
 
        self.numbering = dict((pages[i].urlname(), i) for i in range(len(pages)))
        self.list = [Translations(languages=languages) for i in range(len(pages))]
 
        # pre-load pages
        allInterwiki = []
        pages = [self.removeSection(page) for page in self.preloadPages(pages)]
        for page in pages:
            number = self.getNumber(page)
            self.list[number].addPage(page)
 
            if page.exists():
                interwikis = [self.removeSection(interwiki) for interwiki in page.interwiki() if interwiki.site().language() in self.languages]
                for interwiki in interwikis:
                    self.setNumber(interwiki, number)
                    allInterwiki.append(interwiki)
 
        for page in self.preloadPages(allInterwiki):
            self.list[self.getNumber(page)].addPage(page)
 
    def __iter__(self):
        for translations in self.list:
            yield translations
 
    def removeSection(self, page):
        page._section = None
        return page
 
    def getNumber(self, page):
        key = page.urlname()
        return self.numbering[key] if key in self.numbering else -1
 
    def setNumber(self, page, number):
        self.numbering[page.urlname()] = number
 
    def preloadPages(self, pages, resolveRedirects=True, preserveOrdering = True):
        # do not load pages that have been loaded already
        result = [page for page in pages if hasattr(page, '_contents')]
        result.extend([page for page in pagegenerators.PreloadingGenerator([page for page in pages if not hasattr(page, '_contents')], pageNumber=self.preloadNumber)])
 
 
        if resolveRedirects:
            possibleRedirects = list(result)
            result = []
            while len(possibleRedirects):
                gen = self.preloadPages(possibleRedirects, resolveRedirects=False, preserveOrdering = False)
                possibleRedirects = []
                for page in gen:
                    if page.isRedirectPage():
                        target = page.getRedirectTarget()
                        self.setNumber(target, self.getNumber(page))
                        possibleRedirects.append(target)
                    else:
                        result.append(page)
 
        if preserveOrdering:
            result.sort(key=self.getNumber)
 
        return result
 
    def getLanguages(self):
        return self.languages
 
 
 
class StatisticsCalculator():
 
    def __init__(self, translationList, languageNames = {}, languageWeights = {}):
        self.translationList = translationList
        self.languages = self.translationList.getLanguages()
        self.languageNames = languageNames
        self.languageWeights = languageWeights
 
        self.stats = [self.StatisticsForTranslations(translations) for translations in self.translationList]
        for i in range(len(self.stats)):
            self.stats[i]['number'] = i+1
        self.statsPerLanguage = self.CalculateStatsPerLanguage()
 
    def StatisticsForPage(self, page):
        if page is None or not page.exists():
            return {'char_count': 0, 'clear_size': 0, 'type': 'absent'}
 
        text = page.get().replace('\r\n', '\n')
        articleCharCount = self.GetCharCount(text)
        interwikiLength = self.GetInterwikiLength(text)
        commentsLength = self.GetCommentLength(text)
        clearArticleSize = (articleCharCount - interwikiLength - commentsLength)*self.languageWeights[page.site().language()]
        articleType = self.GetArticleType(clearArticleSize)
 
        return {'char_count': articleCharCount, 'clear_size': clearArticleSize, 'type': articleType}
 
    def StatisticsForTranslations(self, translations):
        result = {'translations':translations}
        for language in self.languages:
            result[language] = self.StatisticsForPage(translations.getPage(language))
        return result
 
    def CalculateStatsPerLanguage(self):
        overallStats = dict((language, {
            'total_size': 0,
            'absent': 0,
            'stubs': 0,
            'articles': 0,
            'longarticles': 0,
 
        }) for language in self.languages)
 
        for language in self.languages:
            for stat in self.stats:
                articleType = stat[language]['type']
                overallStats[language][articleType] += 1
                overallStats[language]['total_size'] += stat[language]['clear_size']
 
            absent       = overallStats[language]['absent']
            stubs        = overallStats[language]['stubs']
            articles     = overallStats[language]['articles']
            longarticles = overallStats[language]['longarticles']
            totalCount   = absent + stubs + articles + longarticles
 
            overallStats[language]['total_count'] = totalCount
            overallStats[language]['rating'] = self.GetScore(totalCount, absent, stubs, articles, longarticles)
            overallStats[language]['average_size'] = self.GetAverageSize(totalCount, overallStats[language]['total_size'])
 
        return overallStats
 
    def GetArticleType(self, charCount):
       if not charCount:
          return 'absent'
       if charCount < 10000:
          return 'stubs'
       if charCount < 30000:
          return 'articles'
       return 'longarticles'
 
    def GetInterwikiLength(self, text):
        result = 0
        interwikiPattern = re.compile(r'\[\[([a-zA-Z\-]+)\s?:(?:[^\[\]\n]*)\]\]\n*')
        for interwiki in interwikiPattern.finditer(text):
            lang = interwiki.group(1)
            if lang in wikipedia.Family('wikipedia').langs.keys():
                result += len(interwiki.group(0))
 
        return result
 
    def GetCommentLength(self, text):
        comment_len   = 0
        comment_last  = 0
        comment_first = text.find(u'<!--', comment_last)
        while comment_first > -1:
            comment_last = text.find(u'-->', comment_first)
            if comment_last == -1:
               comment_last = comment_first + 4
 
            comment_len += (comment_last - comment_first) - 4
            comment_first = text.find(u'<!--', comment_last)
 
        return comment_len
 
    def GetCharCount(self, text):
        return len(text)
 
    def GetScore(self, totalCount, absent, stubs, articles, longarticles):
        max_score = totalCount * 9
        raw_score = stubs + (articles*4) + (longarticles*9)
        if max_score > 0:
            score = 100.0 * raw_score / max_score
        else:
            score = 0
        return score
 
    def GetAverageSize(self, totalCount, totalSize):
        if totalCount > 0:
           avg_size = int(round(totalSize / totalCount))
        else:
           avg_size = 0
        return avg_size
 
 
    def FormatResults(self, outputPageName, localLanguage = 'uk'):
        result = u'{{-start-}}{{-titlestart-}}' + outputPageName + u'{{-titlestop-}}'
        for language in self.languages:
	    overallStats = self.statsPerLanguage[language]
            result += u';' + self.languageNames[language] + u'\n'
	    result += u'Рейтинг: {0:.2f} ({1} відсутніх, {2} коротких, {3} середніх, {4} довгих)\n\n'.format(overallStats['rating'], overallStats['absent'], overallStats['stubs'], overallStats['articles'], overallStats['longarticles'])
	    result += u'Середній розмір статей: {0}\n\n'.format(overallStats['average_size'])
	    
        result += u'Оновлено: %s\n' % datetime.date.today()
        result += u'{| class="wikitable sortable" \n|- \n! №\n'
        for language in self.languages:
            result += u'! ' + self.languageNames[language] + u'\n'
            if language == localLanguage:
                result += u'! Cимволів\n'
	        result += u'! Нормований\n'
           
        for stat in self.stats:
            translations = stat['translations']
 
            articleType = stat[localLanguage]['type']
 
            if articleType == 'stubs':
                result += u"|- style='background:#ffe0e0'\n"
            elif articleType == 'articles':
                result += u"|- style='background:#ffffe0'\n"
            elif articleType == 'longarticles':
                result += u"|- style='background:#e0ffe0'\n"
            else:
                result += u"|- \n"
 
            result += u'| {0} '.format(stat['number'])
 
            for language in self.languages:
                page = translations.getPage(language)
                if not page is None and page.exists():
                    if language == localLanguage:
                        result += u' || {0}'.format(page.title(asLink=True, textlink=True))
                    else:
                        result += u' || [[:{0}:{1}|{2}]]'.format(language, page.title(), stat[language]['clear_size'])
                else:
                    result += u' || відсутня'
 
                if language==localLanguage:
                    result += u' || ALIGN=RIGHT | {0}'.format(stat[language]['char_count'])
		    result += u' || ALIGN=RIGHT | {0}'.format(stat[language]['clear_size'])
 
            result += '\n'
 
        result += u'|}{{-stop-}}'
        return result
 
 
#main code
wikipedia.output('Reading list from \'list.txt\'...')
pages = [page for page in pagegenerators.TextfilePageGenerator('list.txt')]
 
wikipedia.output(u'Getting interwikis for every page...')
translationList = TranslationsList(pages, languages=languages)
 
wikipedia.output(u'Calculating statistics...')
stats = StatisticsCalculator(translationList, languageNames, languageWeights)
 
wikipedia.output(u'Writing stats to \'stats.txt\'...')
with open('stats.txt', 'w') as f:
    f.write(stats.FormatResults(outputPage, localLanguage).encode("utf_8"))
 
wikipedia.output(u'Writing list of articles to \'listLocal.txt\'...')
with open('listLocal.txt', 'w') as f:
    for translation in translationList:
        page = translation.getPage(localLanguage)
        if not page is None and page.exists():
            f.write("{0}\n".format(page.title(asLink=True).encode("utf_8")))

5. Виконати обидва скрипти. В консолі перейти в директорію pywikipedia і набрати

python getList1000.py

python stats.py

  • Відкрити stats.txt і копіпастнути все на сторінку, прибравши позначки початку і кінця файлу для автоматичного завантаження. Можна завантажити роботом, але легше ручками.

--Дядько Ігор 18:50, 25 жовтня 2011 (UTC)Відповісти

Здається, працює без проблем лише під Лінуксом - під Windows виникають проблеми з кодуваннями назв статей --Ілля 19:06, 25 жовтня 2011 (UTC)Відповісти
У мене нема досвіду роботи з python під Windows. Можна спитати когось, хто це знає - інших власників ботів. --Дядько Ігор 19:17, 25 жовтня 2011 (UTC)Відповісти
Повернутися на сторінку користувача «Дядько Ігор/Прохання оновити статистику! (20.10.2011 - 25.10.2011)».