Frage

Ich Schreibe eine Anwendung, die mehrere threads ausgeführt werden, und wollen zu drosseln der CPU/memory Nutzung dieser threads.

Es ist ein ähnliche Frage für C++,, aber ich möchte, um zu versuchen und vermeiden Sie die Verwendung von C++, JNI, wenn möglich.Ich weiß, das ist vielleicht nicht möglich, mit einer Sprache auf höherer Ebene, aber ich bin neugierig zu sehen, ob jemand irgendwelche Ideen hat.

EDIT: Hinzugefügt wurde ein Kopfgeld;Ich würde gerne einige wirklich gute, durchdachte Ideen auf dieser.

EDIT 2: Die situation, die ich benötigen diese für die Ausführung anderer Leute code auf meinem server.Im Grunde ist es völlig willkürlichen code mit die einzige Garantie, dass es wird eine main-Methode der Klasse file.Derzeit, mehrere völlig unterschiedlichen Klassen, die geladen werden zur Laufzeit ausgeführt werden, die gleichzeitig als separate threads.

Die Art, wie es geschrieben steht, es wäre ein Schmerz zu überarbeiten, um erstellen Sie separate Prozesse für jede Klasse, die ausgeführt wird.Wenn das ist die einzige gute Möglichkeit, um die Speichernutzung über das VM-Argumente, dann soll es so sein.Aber ich würde gerne wissen, ob es einen Weg gibt, es zu tun mit threads.Sogar als separater Prozess, ich möchte in der Lage sein, irgendwie zu begrenzen CPU-Auslastung, da, wie ich bereits erwähnt habe, einige dieser ausgeführt werden auf einmal.Ich will nicht eine endlos-Schleife zu hog all die Ressourcen.

EDIT 3: Ein einfacher Weg, um die Ungefähre Größe des Objekts ist mit java Instrumentation Klassen;insbesondere die getObjectSize Methode.Beachten Sie, dass es einige spezielle Konfiguration erforderlich, um dieses tool zu verwenden.

War es hilfreich?

Lösung

Wenn ich Ihr Problem zu verstehen, wäre eine Möglichkeit, adaptiv sein, um die Fäden zu schlafen, ähnlich wie Video-Wiedergabe in Java erfolgt. Wenn Sie wissen, dass Sie 50% Kernnutzung wollen, sollte der Algorithmus Ihres ungefähr 0,5 Sekunden schlafen - möglicherweise innerhalb einer Sekunde verteilt (zum Beispiel 0,25 sec Berechnung, 0,25 sec Schlafes, e.t.c.). Hier ist ein

Andere Tipps

Sie können eine Menge von Informationen über CPU- und Speichernutzung über JMX , aber ich glaube nicht, dass eine aktive Manipulation ermöglicht.

Für die CPU-Auslastung bis zu einem gewissen Grad zu steuern, können Sie Thread.setPriority () .

Wie für Speicher, gibt es nicht so etwas wie Pro-Thread-Speicher. Das Konzept von Java-Threads bedeutet Shared Memory. Die einzige Möglichkeit, die Speichernutzung zu steuern, ist über die Kommandozeilenoptionen wie -Xmx, aber es gibt keine Möglichkeit, die Einstellungen zur Laufzeit zu manipulieren.

Pflege von Java Foren . Grundsätzlich Ihre Ausführung Timing und dann warten, wenn Ihr zu viel Zeit. Wie in dem ursprünglichen Thread erwähnt, diese in einem separaten Thread ausgeführt wird und der Arbeits-Thread zu unterbrechen gibt genauere Ergebnisse, als Willen Lungswerte über die Zeit.

import java.lang.management.*;

ThreadMXBean TMB = ManagementFactory.getThreadMXBean();
long time = new Date().getTime() * 1000000;
long cput = 0;
double cpuperc = -1;

while(true){

if( TMB.isThreadCpuTimeSupported() ){
    if(new Date().getTime() * 1000000 - time > 1000000000){ //Reset once per second
        time = new Date().getTime() * 1000000;
        cput = TMB.getCurrentThreadCpuTime();
    }

    if(!TMB.isThreadCpuTimeEnabled()){
        TMB.setThreadCpuTimeEnabled(true);
    }

    if(new Date().getTime() * 1000000 - time != 0)
        cpuperc = (TMB.getCurrentThreadCpuTime() - cput) / (new Date().getTime() *  1000000.0 - time) * 100.0;                  
    }
//If cpu usage is greater then 50%
if(cpuperc > 50.0){
     //sleep for a little bit.
     continue;
}
//Do cpu intensive stuff
}

Sie können zu den Themen unterschiedliche Prioritäten zuweisen, damit der relevanteste Thread häufiger geplant bekommen.

Schauen Sie sich diese Antwort , um zu sehen, ob das hilft.

Wenn alle laufenden Thread die gleiche Priorität haben sie wie folgt ausführen können:

t1, t2, t3,     t1, t2, t3,   t1, t2, t3

Wenn Sie eine andere Priorität zu einem von ihnen zuweisen kann es wie folgt aussehen:

t1, t1, t1, t1,    t2,    t1, t1, t1 t3.

Das heißt, der erste Thread läuft „öfter“, dass der Rest.

Wenn Sie das Gewinde in einem separaten Prozess, Sie können Kappe die Speicherauslastung und die Anzahl der CPUs oder ändern Sie die Priorität des threads.

Jedoch, alles, was Sie tun, ist wahrscheinlich hinzufügen, um Aufwand und die Komplexität, die oft kontraproduktiv ist.

Es sei denn, Sie erklären können, warum würden Sie wollen, dies zu tun (z.B.Sie haben eine schlecht geschriebene Bibliothek, die Sie nicht Vertrauen, und kann nicht Unterstützung) würde ich vorschlagen, Sie nicht brauchen, um.

Der Grund, es ist nicht leicht zu beschränken, die Speicherauslastung ist es nur ein Haufen, die gemeinsam.Also ein Objekt, das in einem thread ist nutzbar in einem anderen und nicht zugeordnet ist, zu einem Faden oder einem anderen.

Begrenzung der CPU-Auslastung bedeutet, stoppen alle threads, so dass Sie nicht alles tun, aber ein besserer Ansatz ist zu machen Sie sicher, dass der thread, don ' T waste CPU und sind nur aktiv, die Arbeit, die getan werden muss, in dem Fall, dass Sie würde nicht wollen, Sie zu stoppen, es zu tun.

Warum nicht statt „Einfädeln“ tun kooperatives Multitasking zu tun, wäre interessant zu sehen, wenn Sie manipulieren können http: / /www.janino.net/ ein Programm für eine bestimmte Zeit / set von intstructions laufen, dann stoppen und das nächste Programm. Zumindest diese Weise seines fair, gibt jeder die gleiche Zeitscheibe ...

Thread.setPriority () kann helfen, aber es erlaubt Ihnen nicht, die CPU von einem Thread verwendet Kappe. In der Tat habe ich nicht von jedem Java-Bibliothek gehört, dass dies der Fall ist.

Es könnte möglich sein, eine solche Einrichtung zu implementieren vorausgesetzt, dass Ihre Themen sind bereit, zu kooperieren. Der Schlüssel ist es, die Fäden haben periodisch in einem benutzerdefinierten scheduler nennen, und haben die Thread-Scheduler die CPU-Auslastung Monitor JMX. Aber das Problem ist, dass, wenn einiger Thread nicht den Scheduler Anruf macht oft genug, um es auch die Drosselgrenzen nicht überschreiten. Und es gibt nichts, was man einen Faden tun kann, die in einer Schleife stecken bleiben.

Ein weiterer theoretischer Weg zur Umsetzung wäre Isolaten zu verwenden. Leider werden Sie sich schwer einen allgemeinen Zweck JVM zu finden, die Isolate implementiert. Außerdem lassen sich die Standard-APIs Sie nur das Isolat steuern, nicht die Fäden innerhalb des Isolats.

Die einzige Möglichkeit, Themen-CPU-Nutzung einschränken kann, ist entweder durch Block auf eine Ressource oder Ausbeute () aufrufen häufig.

Dies ist nicht die CPU-Auslastung unter 100% begrenzen gibt aber auch andere Threads und Prozesse mehr Zeitscheiben.

CPU zu verringern, Sie möchten, dass Ihre Themen schlafen innerhalb des gemeinsamen , wenn und , während Schleifen.

while(whatever) {
    //do something
    //Note the capitol 'T' here, this sleeps the current thread.
    Thread.sleep(someNumberOfMilliSeconds);
}

Schlafen für ein paar hundert Millisekunden wird stark CPU-Auslastung mit wenig bis gar kein spürbares Ergebnis auf der Leistung.

reduzieren

Wie für den Speicher, würde ich einen Profiler zu den einzelnen Threads laufen und einige Performance-Tuning tun. Wenn Sie aus der Menge an Speicher zur Verfügung fädeln gedrosselt denke ich, ein aus der Erinnerung Ausnahme oder verhungert Thread wahrscheinlich ist. Ich würde die JVM vertrauen so vielen Speicher zu schaffen, wie der Faden benötigt und die Arbeit an den Speicherverbrauch zu reduzieren, indem zu jedem gegebenen Zeitpunkt nur wesentliche Objekte in Rahmen zu halten.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top