как получить ProcessThread.TotalProcessorTime текущего потока - PullRequest
0 голосов
/ 24 января 2011

хорошо, я использую ThreadPool для запуска потоков. Внутри кода я пытаюсь выяснить, сколько процессорного времени он фактически использовал. Я читал, что есть ProcessThread. Свойство TotalProcessorTime для этого (http://msdn.microsoft.com/en-us/library/system.diagnostics.processthread.totalprocessortime.aspx), но я просто не могу прочитать его. Так как мне получить его для текущего потока?

Ответы [ 2 ]

3 голосов
/ 25 января 2011

Я пытался сделать то же самое ... узнать, сколько процессора потребляет конкретный поток.В следующем коде я могу определить текущий поток, в котором выполняется WorkHard.Однако переменные intitialTicks и finalTicks имеют currentProcessThread.TotalProcessorTime.Ticks до и после выполнения сложной для вычисления функции, но обе имеют одно и то же значение, поэтому разница равна нулю

    public void WorkHard()
    {
        long initialTicks, finalTicks, deltaTicks;
        byte f;
        bool threadFound;

        ProcessThreadCollection currentProcessThreads;
        ProcessThread currentProcessThread = null;

        int m_currentThreadId = kernel32.GetCurrentThreadId();

        while (m_keepWorking)
        {
            f = (byte)rnd.Next(31);
            System.Threading.Thread.Sleep(f*25);
            threadFound = false;
            currentProcessThreads = Process.GetCurrentProcess().Threads;

            foreach (ProcessThread t in currentProcessThreads)
            {
                if (t.Id == m_currentThreadId)
                {
                    currentProcessThread = t;
                    threadFound = true;
                    break;
                }
            }

            initialTicks = threadFound ? currentProcessThread.TotalProcessorTime.Ticks : 0; 
            fibonacci(f);
            finalTicks = threadFound ? currentProcessThread.TotalProcessorTime.Ticks : 0;
            deltaTicks = finalTicks - initialTicks;
            lock (workerLogFile.BaseStream)
            {
                workerLogFile.WriteLine(string.Concat(m_minionName, " finished calculating fib(", f.ToString(), ") at ", DateTime.Now.ToString("yyyy.MM.dd HH:mm:ss.ffff"), " on threadId[", m_currentThreadId.ToString(), "]. Process required ", finalTicks.ToString()," - ", initialTicks.ToString()," = ", deltaTicks.ToString(), " ticks"));
            }

            OnMinionDoneEvent(new minionEventArgs(String.Concat(m_minionName, ", on thread ", m_currentThreadId.ToString("000000"), ", done working on Fibonacci(", f.ToString(), ")"), finalTicks - initialTicks));
        }
        lock (workerLogFile.BaseStream)
        {
            workerLogFile.WriteLine(string.Concat(m_minionName, " called to rest at ", DateTime.Now.ToString("yyyy.MM.dd HH:mm:ss.ffff"), " on threadId[", m_currentThreadId.ToString(), "]."));
        }
2 голосов
/ 24 января 2011

Несколько точек:

1) Чтобы получить правильный поток процесса через ProcessThread. TotalProcessorTime вам понадобится собственный идентификатор потока

2) Похоже, вы сравниваете идентификатор управляемого потока (через Thread.CurrentThread.Name) с собственным идентификатором потока, чтобы получить текущий поток в пространстве имен System.Diagnostics. Помните, что идентификатор управляемого потока! = ProcessThreadID. Вам нужно будет использовать функцию GetCurrentThreadId http://msdn.microsoft.com/en-us/library/ms683183(VS.85).aspx

3) Потоки пула потоков могут быть переработаны, поэтому TotalProcessorTime для пула потоков может быть больше, чем вы ожидаете

4) Если вы профилируете использование потока, может быть проще использовать профилировщик потока в Visual Studio Ultimate или другой хороший профилировщик (например, ANTS, DotTrace, SciTech)

...