Inhaltsverzeichnis
registerNatives-Methode
getClass-Methode
hashCode-Methode
Gleich-Methode
Klonmethode
toString-Methode
notify方法
notifyAll方法
wait方法
finalize方法
Heim Java javaLernprogramm Java-Beispielanalyse von Object aus der Perspektive des JDK-Quellcodes

Java-Beispielanalyse von Object aus der Perspektive des JDK-Quellcodes

Jul 18, 2017 am 09:46 AM
java object 实例分析

Object ist die übergeordnete Klasse aller Klassen, was bedeutet, dass alle Klassen in Java direkt oder indirekt von der Object-Klasse erben. Wenn Sie beispielsweise beiläufig eine Klasse A erstellen, obwohl dies nicht explizit angegeben ist, wird standardmäßig „extends Object“ verwendet. Die drei Punkte „…“ nach
zeigen an, dass eine unbestimmte Anzahl von Parametern akzeptiert werden kann. Die alte Schreibweise ist Object args [], aber in der neuen Version von Java wird empfohlen, ... zu verwenden, um es auszudrücken. Beispielsweise ist

public void getSomething(String ...  strings)(){}
Nach dem Login kopieren

object die übergeordnete Klasse aller Klassen in Java, was bedeutet, dass alle Klassen, unabhängig davon, ob sie von Ihnen selbst oder im System erstellt wurden, von der Objektklasse erben, also alle Klassen Die Objektklasse kann bei jeder Gelegenheit ersetzt werden. Nach dem Liskov-Substitutionsprinzip kann eine Unterklasse ihre übergeordnete Klasse jederzeit ersetzen, aber die übergeordnete Klasse ersetzt möglicherweise nicht unbedingt ihre Unterklasse. In Java wird oft gesagt, dass dies der Fall ist ein Objekt. Das ist die Wahrheit! Die Objektklasse verkörpert die vier Hauptmerkmale Polymorphismus, Vererbung, Kapselung und Abstraktion im Oop-Denken!

Die Objektklasse ist die Basisklasse aller Klassen, kein Datentyp. Weitere Informationen hierzu finden Sie in der JDK-Dokumentation. Alle Klassen erben von Object.

Objekt ...Objekte Diese Art der Parameterdefinition ist ein polymorpher Ausdruck, wenn die Methodenparameter unsicher sind. Das heißt, diese Methode kann mehrere Parameter übergeben und die Anzahl der Parameter ist ungewiss. Auf diese Weise müssen Sie im Methodenkörper eine entsprechende Verarbeitung durchführen. Da Object die Basisklasse ist, wird die Parameterform Object...objects verwendet, um die Verwendung aller von Object geerbten Objekte als Parameter zu ermöglichen. Diese Methode sollte in der Praxis relativ selten angewendet werden.

Object[] obj ist eine Parameterform, die aus einem Object-Array besteht. Beachten Sie, dass die Parameter dieser Methode fest sind und ein Object-Array sind. Die in diesem Array gespeicherten Elemente können Objekte aller Klassen sein, die von Object erben.
Es wird empfohlen, dass Sie für diese grundlegenden Dinge mehrmals „Think in Java“ lesen

Java-Objekt ist die übergeordnete Klasse aller anderen Klassen. Aus Sicht der Vererbung ist es die Wurzel der obersten Ebene Es handelt sich also auch um die einzige A-Klasse ohne übergeordnete Klasse. Es enthält einige häufig verwendete Methoden von Objekten, wie z. B. getClass, hashCode, equals, clone, toString, notify, wait und andere gängige Methoden. Daher müssen andere Klassen diese Methoden nach dem Erben von Object nicht wiederholt implementieren. Bei den meisten dieser Methoden handelt es sich um native Methoden, die im Folgenden detailliert analysiert werden.

Der Hauptcode lautet wie folgt:

public class Object {
  private static native void registerNatives();
  static {
    registerNatives();
  }
  public final native Class<?> getClass();
  public native int hashCode();
  public boolean equals(Object obj) {
    return (this == obj);
  }
  protected native Object clone() throws CloneNotSupportedException;
  public String toString() {
    return getClass().getName() + "@" + Integer.toHexString(hashCode());
  }

  public final native void notify();

  public final native void notifyAll();

  public final native void wait(long timeout) throws InterruptedException;

  public final void wait(long timeout, int nanos) throws InterruptedException {
    if (timeout < 0) {
      throw new IllegalArgumentException("timeout value is negative");
    }

    if (nanos < 0 || nanos > 999999) {
      throw new IllegalArgumentException("nanosecond timeout value out of range");
    }

    if (nanos > 0) {
      timeout++;
    }

    wait(timeout);
  }

  public final void wait() throws InterruptedException {
    wait(0);
  }

  protected void finalize() throws Throwable {}
}
Nach dem Login kopieren

registerNatives-Methode

Da die registerNatives-Methode durch einen statischen Block geändert wird, wird diese Methode ausgeführt, wenn die Object-Klasse Die entsprechende lokale Methode ist Java_java_lang_Object_registerNatives, wie unten gezeigt,

JNIEXPORT void JNICALL
Java_java_lang_Object_registerNatives(JNIEnv *env, jclass cls)
{
    (*env)->RegisterNatives(env, cls,
methods, sizeof(methods)/sizeof(methods[0]));
}
Nach dem Login kopieren

kann gesehen werden, dass sie indirekt die Methode der JNINativeInterface_-Struktur aufruft Es kann einfach so gesehen werden. Was es bewirkt, ist wahrscheinlich die Konvertierung der entsprechenden Methodennamen in lokale Funktionen der Java-Schicht. Dies erleichtert der Ausführungs-Engine das Aufrufen von C/C++-Funktionen basierend auf diesen Korrespondenztabellen, wenn sie Bytecode ausführt. Wie unten gezeigt, können diese Methoden registriert werden, und die Ausführungs-Engine kann sie übergeben Beziehung beim Ausführen der hashCode-Methode, um die JVM_IHashCode-Funktion von JVM zu finden, wobei ()I auch wissen kann, dass der Typ auf der Java-Ebene in den Typ int konvertiert werden soll. Diese Zuordnung kann tatsächlich als Zuordnung von Zeichenfolgen zu Funktionszeigern angesehen werden.

static JNINativeMethod methods[] = {
    {"hashCode",    "()I",                    (void *)&JVM_IHashCode},
    {"wait",        "(J)V",                   (void *)&JVM_MonitorWait},
    {"notify",      "()V",                    (void *)&JVM_MonitorNotify},
    {"notifyAll",   "()V",                    (void *)&JVM_MonitorNotifyAll},
    {"clone",       "()Ljava/lang/Object;",   (void *)&JVM_Clone},
};
Nach dem Login kopieren

getClass-Methode

getClass-Methode ist auch eine lokale Methode, und die entsprechende lokale Methode ist Java_java_lang_Object_getClass, wie folgt:

JNIEXPORT jclass JNICALL
Java_java_lang_Object_getClass(JNIEnv *env, jobject this)
{
    if (this == NULL) {
        JNU_ThrowNullPointerException(env, NULL);
        return 0;
    } else {
        return (*env)->GetObjectClass(env, this);
    }
}
Nach dem Login kopieren

Also die Hauptsache Was hier zu sehen ist, ist die GetObjectClass-Funktion, die Klasse in der Java-Schicht entspricht klassOop in der C++-Schicht, sodass Metadaten und Methodeninformationen über die Klasse über sie abgerufen werden können.

JNI_ENTRY(jclass, jni_GetObjectClass(JNIEnv *env, jobject obj))
  JNIWrapper("GetObjectClass");
  DTRACE_PROBE2(hotspot_jni, GetObjectClass__entry, env, obj);
  klassOop k = JNIHandles::resolve_non_null(obj)->klass();
  jclass ret =
    (jclass) JNIHandles::make_local(env, Klass::cast(k)->java_mirror());
  DTRACE_PROBE1(hotspot_jni, GetObjectClass__return, ret);
  return ret;
JNI_END
Nach dem Login kopieren

hashCode-Methode

Aus der vorherigen registerNatives-Methode zum Registrieren mehrerer lokaler Methoden geht hervor, dass die der hashCode-Methode entsprechende Funktion JVM_IHashCode ist, also

JVM_ENTRY(jint, JVM_IHashCode(JNIEnv* env, jobject handle))
  JVMWrapper("JVM_IHashCode");
  // as implemented in the classic virtual machine; return 0 if object is NULL
  return handle == NULL ? 0 : ObjectSynchronizer::FastHashCode (THREAD, JNIHandles::resolve_non_null(handle)) ;
JVM_END
Nach dem Login kopieren

für Die Logik der Hashcode-Generierung wird durch die synchronizer.cpp-Funktion von get_next_hash bestimmt, und die Implementierung ist relativ kompliziert. Es gibt verschiedene Generierungsstrategien entsprechend unterschiedlichen Hashcode-Werten und schließlich einem Hash Für die Verarbeitung wird eine Maske verwendet.

static inline intptr_t get_next_hash(Thread * Self, oop obj) {
  intptr_t value = 0 ;
  if (hashCode == 0) {
     value = os::random() ;
  } else
  if (hashCode == 1) {
     intptr_t addrBits = intptr_t(obj) >> 3 ;
     value = addrBits ^ (addrBits >> 5) ^ GVars.stwRandom ;
  } else
  if (hashCode == 2) {
     value = 1 ;            // for sensitivity testing
  } else
  if (hashCode == 3) {
     value = ++GVars.hcSequence ;
  } else
  if (hashCode == 4) {
     value = intptr_t(obj) ;
  } else {
     unsigned t = Self->_hashStateX ;
     t ^= (t << 11) ;
     Self->_hashStateX = Self->_hashStateY ;
     Self->_hashStateY = Self->_hashStateZ ;
     Self->_hashStateZ = Self->_hashStateW ;
     unsigned v = Self->_hashStateW ;
     v = (v ^ (v >> 19)) ^ (t ^ (t >> 8)) ;
     Self->_hashStateW = v ;
     value = v ;
  }

  value &= markOopDesc::hash_mask;
  if (value == 0) value = 0xBAD ;
  assert (value != markOopDesc::no_hash, "invariant") ;
  TEVENT (hashCode: GENERATE) ;
  return value;
}
Nach dem Login kopieren

Gleich-Methode

Dies ist eine nicht lokale Methode, und die Beurteilungslogik ist ebenfalls sehr einfach, direkter == Vergleich.

Klonmethode

Aus der lokalen Methodentabelle wissen wir, dass die der Klonmethode entsprechende lokale Funktion JVM_Clone ist. Die Klonmethode implementiert hauptsächlich die Klonfunktion des Objekts und generiert eine Identisches neues Objekt basierend auf dem Objekt (wir Wenn die Eigenschaften gemeinsamer Klassenobjekte primitive Typen sind, wird der Wert geklont, wenn es sich jedoch um Objekte handelt, wird die Adresse des Objekts geklont). Um das Klonen zu implementieren, muss eine Java-Klasse die Cloneable-Schnittstelle implementieren. if (!klass->is_cloneable()) Hier wird überprüft, ob die Schnittstelle implementiert ist. Bestimmen Sie dann, ob es sich um ein Array handelt, und weisen Sie in zwei Fällen Speicherplatz zu. Das neue Objekt ist new_obj und kopiert und legt dann die C++-Schichtdatenstruktur von new_obj fest. Schließlich wird es in den Jobject-Typ konvertiert, um die Konvertierung in den Object-Typ der Java-Schicht zu erleichtern.

JVM_ENTRY(jobject, JVM_Clone(JNIEnv* env, jobject handle))
  JVMWrapper("JVM_Clone");
  Handle obj(THREAD, JNIHandles::resolve_non_null(handle));
  const KlassHandle klass (THREAD, obj->klass());
  JvmtiVMObjectAllocEventCollector oam;

  if (!klass->is_cloneable()) {
    ResourceMark rm(THREAD);
    THROW_MSG_0(vmSymbols::java_lang_CloneNotSupportedException(), klass->external_name());
  }

  const int size = obj->size();
  oop new_obj = NULL;
  if (obj->is_javaArray()) {
    const int length = ((arrayOop)obj())->length();
    new_obj = CollectedHeap::array_allocate(klass, size, length, CHECK_NULL);
  } else {
    new_obj = CollectedHeap::obj_allocate(klass, size, CHECK_NULL);
  }
  Copy::conjoint_jlongs_atomic((jlong*)obj(), (jlong*)new_obj,
                               (size_t)align_object_size(size) / HeapWordsPerLong);
  new_obj->init_mark();

  BarrierSet* bs = Universe::heap()->barrier_set();
  assert(bs->has_write_region_opt(), "Barrier set does not have write_region");
  bs->write_region(MemRegion((HeapWord*)new_obj, size));

  if (klass->has_finalizer()) {
    assert(obj->is_instance(), "should be instanceOop");
    new_obj = instanceKlass::register_finalizer(instanceOop(new_obj), CHECK_NULL);
  }

  return JNIHandles::make_local(env, oop(new_obj));
JVM_END
Nach dem Login kopieren

toString-Methode

Die Logik besteht darin, den Klassennamen plus @ plus den hexadezimalen HashCode zu erhalten.

notify方法

此方法用来唤醒线程,final修饰说明不可重写。与之对应的本地方法为JVM_MonitorNotifyObjectSynchronizer::notify最终会调用ObjectMonitor::notify(TRAPS),这个过程是ObjectSynchronizer会尝试当前线程获取free ObjectMonitor对象,不成功则尝试从全局中获取。

JVM_ENTRY(void, JVM_MonitorNotify(JNIEnv* env, jobject handle))
  JVMWrapper("JVM_MonitorNotify");
  Handle obj(THREAD, JNIHandles::resolve_non_null(handle));
  assert(obj->is_instance() || obj->is_array(), "JVM_MonitorNotify must apply to an object");
  ObjectSynchronizer::notify(obj, CHECK);
JVM_END
Nach dem Login kopieren

ObjectMonitor对象包含一个_WaitSet队列对象,此对象保存着所有处于wait状态的线程,用ObjectWaiter对象表示。notify要做的事是先获取_WaitSet队列锁,再取出_WaitSet队列中第一个ObjectWaiter对象,再根据不同策略处理该对象,比如把它加入到_EntryList队列中。然后再释放_WaitSet队列锁。它并没有释放synchronized对应的锁,所以锁只能等到synchronized同步块结束时才释放。

void ObjectMonitor::notify(TRAPS) {
  CHECK_OWNER();
  if (_WaitSet == NULL) {
     TEVENT (Empty-Notify) ;
     return ;
  }
  DTRACE_MONITOR_PROBE(notify, this, object(), THREAD);

  int Policy = Knob_MoveNotifyee ;

  Thread::SpinAcquire (&_WaitSetLock, "WaitSet - notify") ;
  ObjectWaiter * iterator = DequeueWaiter() ;
  if (iterator != NULL) {
     TEVENT (Notify1 - Transfer) ;
     guarantee (iterator->TState == ObjectWaiter::TS_WAIT, "invariant") ;
     guarantee (iterator->_notified == 0, "invariant") ;
     if (Policy != 4) {
        iterator->TState = ObjectWaiter::TS_ENTER ;
     }
     iterator->_notified = 1 ;

     ObjectWaiter * List = _EntryList ;
     if (List != NULL) {
        assert (List->_prev == NULL, "invariant") ;
        assert (List->TState == ObjectWaiter::TS_ENTER, "invariant") ;
        assert (List != iterator, "invariant") ;
     }

     if (Policy == 0) {       // prepend to EntryList
         if (List == NULL) {
             iterator->_next = iterator->_prev = NULL ;
             _EntryList = iterator ;
         } else {
             List->_prev = iterator ;
             iterator->_next = List ;
             iterator->_prev = NULL ;
             _EntryList = iterator ;
        }
     } else
     if (Policy == 1) {      // append to EntryList
         if (List == NULL) {
             iterator->_next = iterator->_prev = NULL ;
             _EntryList = iterator ;
         } else {
            // CONSIDER:  finding the tail currently requires a linear-time walk of
            // the EntryList.  We can make tail access constant-time by converting to
            // a CDLL instead of using our current DLL.
            ObjectWaiter * Tail ;
            for (Tail = List ; Tail->_next != NULL ; Tail = Tail->_next) ;
            assert (Tail != NULL && Tail->_next == NULL, "invariant") ;
            Tail->_next = iterator ;
            iterator->_prev = Tail ;
            iterator->_next = NULL ;
        }
     } else
     if (Policy == 2) {      // prepend to cxq
         // prepend to cxq
         if (List == NULL) {
             iterator->_next = iterator->_prev = NULL ;
             _EntryList = iterator ;
         } else {
            iterator->TState = ObjectWaiter::TS_CXQ ;
            for (;;) {
                ObjectWaiter * Front = _cxq ;
                iterator->_next = Front ;
                if (Atomic::cmpxchg_ptr (iterator, &_cxq, Front) == Front) {
                    break ;
                }
            }
         }
     } else
     if (Policy == 3) {      // append to cxq
        iterator->TState = ObjectWaiter::TS_CXQ ;
        for (;;) {
            ObjectWaiter * Tail ;
            Tail = _cxq ;
            if (Tail == NULL) {
                iterator->_next = NULL ;
                if (Atomic::cmpxchg_ptr (iterator, &_cxq, NULL) == NULL) {
                   break ;
                }
            } else {
                while (Tail->_next != NULL) Tail = Tail->_next ;
                Tail->_next = iterator ;
                iterator->_prev = Tail ;
                iterator->_next = NULL ;
                break ;
            }
        }
     } else {
        ParkEvent * ev = iterator->_event ;
        iterator->TState = ObjectWaiter::TS_RUN ;
        OrderAccess::fence() ;
        ev->unpark() ;
     }

     if (Policy < 4) {
       iterator->wait_reenter_begin(this);
     }

     // _WaitSetLock protects the wait queue, not the EntryList.  We could
     // move the add-to-EntryList operation, above, outside the critical section
     // protected by _WaitSetLock.  In practice that&#39;s not useful.  With the
     // exception of  wait() timeouts and interrupts the monitor owner
     // is the only thread that grabs _WaitSetLock.  There&#39;s almost no contention
     // on _WaitSetLock so it&#39;s not profitable to reduce the length of the
     // critical section.
  }

  Thread::SpinRelease (&_WaitSetLock) ;

  if (iterator != NULL && ObjectMonitor::_sync_Notifications != NULL) {
     ObjectMonitor::_sync_Notifications->inc() ;
  }
}
Nach dem Login kopieren

notifyAll方法

与notify方法类似,只是在取_WaitSet队列时不是取第一个而是取所有。

wait方法

wait方法是让线程等待,它对应的本地方法是JVM_MonitorWait,间接调用了ObjectSynchronizer::wait,与notify对应,它也是对应调用ObjectMonitor对象的wait方法。该方法较长,这里不贴出来了,大概就是创建一个ObjectWaiter对象,接着获取_WaitSet队列锁将ObjectWaiter对象添加到该队列中,再释放队列锁。另外,它还会释放synchronized对应的锁,所以锁没有等到synchronized同步块结束时才释放。

JVM_ENTRY(void, JVM_MonitorWait(JNIEnv* env, jobject handle, jlong ms))
  JVMWrapper("JVM_MonitorWait");
  Handle obj(THREAD, JNIHandles::resolve_non_null(handle));
  assert(obj->is_instance() || obj->is_array(), "JVM_MonitorWait must apply to an object");
  JavaThreadInObjectWaitState jtiows(thread, ms != 0);
  if (JvmtiExport::should_post_monitor_wait()) {
    JvmtiExport::post_monitor_wait((JavaThread *)THREAD, (oop)obj(), ms);
  }
  ObjectSynchronizer::wait(obj, ms, CHECK);
JVM_END
Nach dem Login kopieren

finalize方法

这个方法用于当对象被回收时调用,这个由JVM支持,Object的finalize方法默认是什么都没有做,如果子类需要在对象被回收时执行一些逻辑处理,则可以重写finalize方法。

Das obige ist der detaillierte Inhalt vonJava-Beispielanalyse von Object aus der Perspektive des JDK-Quellcodes. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Erklärung dieser Website
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn

Heiße KI -Werkzeuge

Undresser.AI Undress

Undresser.AI Undress

KI-gestützte App zum Erstellen realistischer Aktfotos

AI Clothes Remover

AI Clothes Remover

Online-KI-Tool zum Entfernen von Kleidung aus Fotos.

Undress AI Tool

Undress AI Tool

Ausziehbilder kostenlos

Clothoff.io

Clothoff.io

KI-Kleiderentferner

AI Hentai Generator

AI Hentai Generator

Erstellen Sie kostenlos Ai Hentai.

Heißer Artikel

R.E.P.O. Energiekristalle erklärten und was sie tun (gelber Kristall)
1 Monate vor By 尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. Beste grafische Einstellungen
1 Monate vor By 尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. So reparieren Sie Audio, wenn Sie niemanden hören können
1 Monate vor By 尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. Chat -Befehle und wie man sie benutzt
1 Monate vor By 尊渡假赌尊渡假赌尊渡假赌

Heiße Werkzeuge

Notepad++7.3.1

Notepad++7.3.1

Einfach zu bedienender und kostenloser Code-Editor

SublimeText3 chinesische Version

SublimeText3 chinesische Version

Chinesische Version, sehr einfach zu bedienen

Senden Sie Studio 13.0.1

Senden Sie Studio 13.0.1

Leistungsstarke integrierte PHP-Entwicklungsumgebung

Dreamweaver CS6

Dreamweaver CS6

Visuelle Webentwicklungstools

SublimeText3 Mac-Version

SublimeText3 Mac-Version

Codebearbeitungssoftware auf Gottesniveau (SublimeText3)

Perfekte Zahl in Java Perfekte Zahl in Java Aug 30, 2024 pm 04:28 PM

Leitfaden zur perfekten Zahl in Java. Hier besprechen wir die Definition, Wie prüft man die perfekte Zahl in Java?, Beispiele mit Code-Implementierung.

Zufallszahlengenerator in Java Zufallszahlengenerator in Java Aug 30, 2024 pm 04:27 PM

Leitfaden zum Zufallszahlengenerator in Java. Hier besprechen wir Funktionen in Java anhand von Beispielen und zwei verschiedene Generatoren anhand ihrer Beispiele.

Weka in Java Weka in Java Aug 30, 2024 pm 04:28 PM

Leitfaden für Weka in Java. Hier besprechen wir die Einführung, die Verwendung von Weka Java, die Art der Plattform und die Vorteile anhand von Beispielen.

Smith-Nummer in Java Smith-Nummer in Java Aug 30, 2024 pm 04:28 PM

Leitfaden zur Smith-Zahl in Java. Hier besprechen wir die Definition: Wie überprüft man die Smith-Nummer in Java? Beispiel mit Code-Implementierung.

Fragen zum Java Spring-Interview Fragen zum Java Spring-Interview Aug 30, 2024 pm 04:29 PM

In diesem Artikel haben wir die am häufigsten gestellten Fragen zu Java Spring-Interviews mit ihren detaillierten Antworten zusammengestellt. Damit Sie das Interview knacken können.

Brechen oder aus Java 8 Stream foreach zurückkehren? Brechen oder aus Java 8 Stream foreach zurückkehren? Feb 07, 2025 pm 12:09 PM

Java 8 führt die Stream -API ein und bietet eine leistungsstarke und ausdrucksstarke Möglichkeit, Datensammlungen zu verarbeiten. Eine häufige Frage bei der Verwendung von Stream lautet jedoch: Wie kann man von einem Foreach -Betrieb brechen oder zurückkehren? Herkömmliche Schleifen ermöglichen eine frühzeitige Unterbrechung oder Rückkehr, aber die Stream's foreach -Methode unterstützt diese Methode nicht direkt. In diesem Artikel werden die Gründe erläutert und alternative Methoden zur Implementierung vorzeitiger Beendigung in Strahlverarbeitungssystemen erforscht. Weitere Lektüre: Java Stream API -Verbesserungen Stream foreach verstehen Die Foreach -Methode ist ein Terminalbetrieb, der einen Vorgang für jedes Element im Stream ausführt. Seine Designabsicht ist

Zeitstempel für Datum in Java Zeitstempel für Datum in Java Aug 30, 2024 pm 04:28 PM

Anleitung zum TimeStamp to Date in Java. Hier diskutieren wir auch die Einführung und wie man Zeitstempel in Java in ein Datum konvertiert, zusammen mit Beispielen.

Java -Programm, um das Kapselvolumen zu finden Java -Programm, um das Kapselvolumen zu finden Feb 07, 2025 am 11:37 AM

Kapseln sind dreidimensionale geometrische Figuren, die aus einem Zylinder und einer Hemisphäre an beiden Enden bestehen. Das Volumen der Kapsel kann berechnet werden, indem das Volumen des Zylinders und das Volumen der Hemisphäre an beiden Enden hinzugefügt werden. In diesem Tutorial wird erörtert, wie das Volumen einer bestimmten Kapsel in Java mit verschiedenen Methoden berechnet wird. Kapselvolumenformel Die Formel für das Kapselvolumen lautet wie folgt: Kapselvolumen = zylindrisches Volumenvolumen Zwei Hemisphäre Volumen In, R: Der Radius der Hemisphäre. H: Die Höhe des Zylinders (ohne die Hemisphäre). Beispiel 1 eingeben Radius = 5 Einheiten Höhe = 10 Einheiten Ausgabe Volumen = 1570,8 Kubikeinheiten erklären Berechnen Sie das Volumen mithilfe der Formel: Volumen = π × R2 × H (4

See all articles