亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

Android React-Native通信數(shù)據(jù)模型分析

 更新時間:2016年10月12日 15:53:57   作者:MegatronKings  
這篇文章主要介紹了Android React-Native通信數(shù)據(jù)模型分析的相關(guān)資料,需要的朋友可以參考下

無論是計算機領(lǐng)域還是日常生活中,我們所言的通信,其核心都是數(shù)據(jù)信息的交換,而數(shù)據(jù)模型的優(yōu)劣對通信效率有著決定性的作用。

在React-Native項目中,Javascript語言與Native兩種語言(Java或OC等)間存在著大量的數(shù)據(jù)交換,也就是所謂的通信。眾所周知,移動APP對性能的要求無比苛刻,如果通信數(shù)據(jù)模型設(shè)計地不合理,很可能引起多線程下的數(shù)據(jù)安全問題,以及應(yīng)用性能問題,比如內(nèi)存泄漏,UI繪制緩慢等。

前面幾篇博客我們詳細(xì)分析過React-Native的通信機制,主要有兩個方向: Java->Bridge->Javascript和Javascript->Bridge->Java。所以,真正的數(shù)據(jù)交換其實發(fā)生在Java與Bridge,Javascript與Bridge兩個環(huán)節(jié)。

Javascript與Bridge間的數(shù)據(jù)通信是借助于Webkit使用Json完成,簡單實用,水到渠成,不多分析。而Java與Bridge間的數(shù)據(jù)通信相比之下就復(fù)雜多了,作為真正運行在設(shè)備上的程序語言,這恰恰是決定整個通信過程效率高低最核心的一環(huán),也是本篇博客研究的內(nèi)容。

Java是Android應(yīng)用程序的本地開發(fā)語言,而Bridge是使用C++開發(fā)的動態(tài)鏈接庫,由Java語言通過JNI的方式調(diào)用。Java與Bridge間的數(shù)據(jù)通信,實質(zhì)是Java和C++兩種程序語言間的數(shù)據(jù)傳輸,而傳遞的方向又分為兩個場景:Java傳輸數(shù)據(jù)給C++ 和C++ 傳輸數(shù)據(jù)給Java。

我們先來看第一種場景。

Java主動向Javascript通信,主要是通過ReactBridge.java類的callFunction方法,將需要調(diào)用的組件(moduleId)、功能(methodId)、數(shù)據(jù)(arguments)三者傳遞到Bridge。

package com.facebook.react.bridge;

public class ReactBridge extends Countable {

 static final String REACT_NATIVE_LIB = "reactnativejni";

 static {
  SoLoader.loadLibrary(REACT_NATIVE_LIB);
 }

 ...

 public native void callFunction(int moduleId, int methodId, NativeArray arguments);

 ...

}

我們可以看到,傳輸?shù)臄?shù)據(jù)類型是NativeArray,來瞧下具體的代碼,位于com.facebook.react.bridge包下:

public abstract class NativeArray {
 static {
  SoLoader.loadLibrary(ReactBridge.REACT_NATIVE_LIB);
 }

 protected NativeArray(HybridData hybridData) {
  mHybridData = hybridData;
 }

 @Override
 public native String toString();

 @DoNotStrip
 private HybridData mHybridData;
}

NativeArray是一個抽象類,其中,只有一個HybridData類型成員變量,由其構(gòu)造方法賦值初始化。

NativeArray還有一個名為ReadableNativeArray的直接子類,和一個名為WritableNativeArray的間接子類,后者是繼承于前者。顧名思義,一個是用于讀數(shù)據(jù),一個是用于寫數(shù)據(jù)。

Java向Bridge傳輸數(shù)據(jù),自然就是寫數(shù)據(jù)了,所以我們先來看WritableNativeArray。

package com.facebook.react.bridge;

public class WritableNativeArray extends ReadableNativeArray implements WritableArray {

 static {
  SoLoader.loadLibrary(ReactBridge.REACT_NATIVE_LIB);
 }

 public WritableNativeArray() {
  super(initHybrid());
 }

 @Override
 public native void pushNull();
 @Override
 public native void pushBoolean(boolean value);
 @Override
 public native void pushDouble(double value);
 @Override
 public native void pushInt(int value);
 @Override
 public native void pushString(String value);

 @Override
 public void pushArray(WritableArray array) {
  Assertions.assertCondition(
    array == null || array instanceof WritableNativeArray, "Illegal type provided");
  pushNativeArray((WritableNativeArray) array);
 }

 @Override
 public void pushMap(WritableMap map) {
  Assertions.assertCondition(
    map == null || map instanceof WritableNativeMap, "Illegal type provided");
  pushNativeMap((WritableNativeMap) map);
 }

 private native static HybridData initHybrid();
 private native void pushNativeArray(WritableNativeArray array);
 private native void pushNativeMap(WritableNativeMap map);
}

里面有7個寫數(shù)據(jù)的native方法,涵蓋了int、string,array,map等不同的數(shù)據(jù)類型和結(jié)構(gòu)。

還有一個名為initHybrid()的native方法,用于創(chuàng)建HybridData類的實例,然后通過構(gòu)造方法給其超父類NativeArray的mHybridData成員變量賦值,具體作用后面來分析,先略過。

接下來,我們來驗證一下WritableNativeArray是否是真正傳輸給Bridge的數(shù)據(jù)類型。

Java調(diào)用Javascript組件,都是由名為JavaScriptModuleInvocationHandler的動態(tài)代理類統(tǒng)一攔截處理的嗎?來回顧一下代碼,位于com.facebook.react.bridge.JavaScriptModuleRegistry.java:

 private static class JavaScriptModuleInvocationHandler implements InvocationHandler {

  private final CatalystInstanceImpl mCatalystInstance;
  private final JavaScriptModuleRegistration mModuleRegistration;

  public JavaScriptModuleInvocationHandler(
    CatalystInstanceImpl catalystInstance,
    JavaScriptModuleRegistration moduleRegistration) {
   mCatalystInstance = catalystInstance;
   mModuleRegistration = moduleRegistration;
  }

  @Override
  public @Nullable Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
   String tracingName = mModuleRegistration.getTracingName(method);
   mCatalystInstance.callFunction(
     mModuleRegistration.getModuleId(),
     mModuleRegistration.getMethodId(method),
     Arguments.fromJavaArgs(args),
     tracingName);
   return null;
  }
 }

callFunction方法傳遞的參數(shù)類型是Arguments.fromJavaArgs(args),具體代碼又如下:

 public static WritableNativeArray fromJavaArgs(Object[] args) {
  WritableNativeArray arguments = new WritableNativeArray();
  for (int i = 0; i < args.length; i++) {
   Object argument = args[i];
   if (argument == null) {
    arguments.pushNull();
    continue;
   }

   Class argumentClass = argument.getClass();
   if (argumentClass == Boolean.class) {
    arguments.pushBoolean(((Boolean) argument).booleanValue());
   } else if (argumentClass == Integer.class) {
    arguments.pushDouble(((Integer) argument).doubleValue());
   } else if (argumentClass == Double.class) {
    arguments.pushDouble(((Double) argument).doubleValue());
   } else if (argumentClass == Float.class) {
    arguments.pushDouble(((Float) argument).doubleValue());
   } else if (argumentClass == String.class) {
    arguments.pushString(argument.toString());
   } else if (argumentClass == WritableNativeMap.class) {
    arguments.pushMap((WritableNativeMap) argument);
   } else if (argumentClass == WritableNativeArray.class) {
    arguments.pushArray((WritableNativeArray) argument);
   } else {
    throw new RuntimeException("Cannot convert argument of type " + argumentClass);
   }
  }
  return arguments;
 }

正如我們猜測的一般,fromJavaArgs靜態(tài)方法返回的是一個新創(chuàng)建的WritableNativeArray對象實例,然后按照數(shù)據(jù)類型,調(diào)用相應(yīng)的push方法。有些特殊的是,int型和float型都當(dāng)成了double型來處理,這樣做并不會造成數(shù)據(jù)的損害。

剛剛說到,WritableNativeArray的所有寫入數(shù)據(jù)的方法都是native方法,即Java層面的通信數(shù)據(jù)全部是直接寫入到Bridge層的,換言之,WritableNativeArray僅僅起到了數(shù)據(jù)傳輸管道的作用。這樣做,有兩個好處:

1、數(shù)據(jù)只在C++存有一份,這樣避免了數(shù)據(jù)具有多個副本,節(jié)省了一部分的內(nèi)存。

2、減小對WritableNativeArray對象的依賴,使其容易釋放,可以由虛擬機GC自動回收內(nèi)存。

那么,在Bridge層中,C++又是如何處理push過來的數(shù)據(jù)的呢?

先來看一下WritableNativeArray中native方法在JNI中動態(tài)注冊的代碼,位于react/jni/OnLoad.cpp中:

static void registerNatives() {
  jni::registerNatives("com/facebook/react/bridge/WritableNativeArray", {
    makeNativeMethod("initHybrid", WritableNativeArray::initHybrid),
    makeNativeMethod("pushNull", WritableNativeArray::pushNull),
    makeNativeMethod("pushBoolean", WritableNativeArray::pushBoolean),
    makeNativeMethod("pushDouble", WritableNativeArray::pushDouble),
    makeNativeMethod("pushInt", WritableNativeArray::pushInt),
    makeNativeMethod("pushString", WritableNativeArray::pushString),
    makeNativeMethod("pushNativeArray", WritableNativeArray::pushNativeArray),
    makeNativeMethod("pushNativeMap", "(Lcom/facebook/react/bridge/WritableNativeMap;)V",
             WritableNativeArray::pushNativeMap),
  });
 }

很明顯,在C++中也存在著一個名為WritableNativeArray的類,具有與著native方法相對應(yīng)的方法,巧的是,它也是繼承于ReadableNativeArray類(注意HybridClass模板類的第二個泛型表示父類):

struct WritableNativeArray
  : public jni::HybridClass<WritableNativeArray, ReadableNativeArray> {
 static constexpr const char* kJavaDescriptor = "Lcom/facebook/react/bridge/WritableNativeArray;";

 WritableNativeArray()
   : HybridBase(folly::dynamic({})) {}

 static local_ref<jhybriddata> initHybrid(alias_ref<jclass>) {
  return makeCxxInstance();
 }

 void pushNull() {
  ...
  array.push_back(nullptr);
 }

 void pushBoolean(jboolean value) {
  ...
  array.push_back(value == JNI_TRUE);
 }

 void pushDouble(jdouble value) {
  ...
  array.push_back(value);
 }

 void pushInt(jint value) {
  ...
  array.push_back(value);
 }

 void pushString(jstring value) {
  ...
  array.push_back(wrap_alias(value)->toStdString());
 }

 void pushNativeArray(WritableNativeArray* otherArray) {
  ...
  array.push_back(std::move(otherArray->array));
  otherArray->isConsumed = true;
 }

 void pushNativeMap(jobject jmap) {
  ...
  array.push_back(std::move(map->map));
  map->isConsumed = true;
 }
 ...
}

看到這里,我們不禁會猜測,C++中的ReadableNativeArray類很可能也是繼承于NativeArray。

當(dāng)然,事實確實是這樣的。在C++中存在著與Java中完全呼應(yīng)的三個類:NativeArray、ReadableNativeArray、WritableNativeArray,命名和繼承關(guān)系都是完全一致的!

而且可以看到,所有的數(shù)據(jù)都被存儲到父類NativeArray的array變量中。

不過,問題來了!

C++中的WritableNativeArray對象和Java中的WritableNativeArray兩個同名對象間是否存在著某種聯(lián)系呢,比如一一映射的關(guān)系?

答案是肯定的! 因為每當(dāng)一個Java層的WritableNativeArray對象被創(chuàng)建,在C++層都會有一個相應(yīng)的WritableNativeArray對象被創(chuàng)建,用來接收J(rèn)ava層push過來的數(shù)據(jù)。

再來回顧下WritableNativeArray.java創(chuàng)建的過程。

public class WritableNativeArray extends ReadableNativeArray implements WritableArray {
  ...
  public WritableNativeArray() {
   super(initHybrid());
  }
  ...
  private native static HybridData initHybrid();
  ...
}

在構(gòu)造WritableNativeArray的時候,會通過initHybrid方法創(chuàng)建一個HybridData對象,并保存到其超父類NativeArray的成員變量mHybridData中。

而HybridData對象又是什么呢?

public class HybridData {
  // Private C++ instance
  private long mNativePointer = 0;
  public HybridData() {
    Prerequisites.ensure();
  }
  public native void resetNative();

  protected void finalize() throws Throwable {
   resetNative();
   super.finalize();
  }
}

public class Prerequisites {
  ...
  public static void ensure() {
    SoLoader.loadLibrary("fbjni");
  }
  ...
}

構(gòu)造函數(shù)中Prerequisites.ensure(),是用來加載fbjni動態(tài)鏈接庫的。

在HybridData 類中,有一個long的私有成員變量,根據(jù)注釋和名字可以猜測與C++指針相關(guān),具體是不是這樣呢?我們來看HybridData對象通過initHybrid()初始化的過程。

代碼位于react/jni/OnLoad.cpp中:

struct WritableNativeArray
  : public jni::HybridClass<WritableNativeArray, ReadableNativeArray> {
  ...

 static local_ref<jhybriddata> initHybrid(alias_ref<jclass>) {
   return makeCxxInstance();
 }

  ... 
}

這里的jhybriddata指的就是HybridData(Java)對象,其是通過typedef方式定義在jni/first-party/jni/fbjni/Hybrid.h中的。

...

struct HybridData : public JavaClass<HybridData> {
 constexpr static auto kJavaDescriptor = "Lcom/facebook/jni/HybridData;";
 void setNativePointer(std::unique_ptr<BaseHybridClass> new_value);
 BaseHybridClass* getNativePointer();
 static local_ref<HybridData> create();
};

...

typedef detail::HybridData::javaobject jhybriddata;

...

facebook在這里對在JNI中創(chuàng)建Java對象的過程做了非常高效的封裝,即JavaClass對象。所有JavaClass的子類都通過一個名為kJavaDescriptor的字符串指針,來描述相對應(yīng)的Java對象類名。

繼續(xù)來看makeCxxInstance()是如何創(chuàng)建HybridData(Java) 對象的。代碼同樣在jni/first-party/jni/fbjni/Hybrid.h中。

class HybridClass : public detail::HybridTraits<Base>::CxxBase {
  ...

 static local_ref<detail::HybridData> makeHybridData(std::unique_ptr<T> cxxPart) {
  auto hybridData = detail::HybridData::create();
  hybridData->setNativePointer(std::move(cxxPart));
  return hybridData;
 }

 template <typename... Args>
 static local_ref<detail::HybridData> makeCxxInstance(Args&&... args) {
  return makeHybridData(std::unique_ptr<T>(new T(std::forward<Args>(args)...)));
 }

  ...
}

結(jié)合下前面的WritableNativeArray(C++)來看

struct WritableNativeArray
  : public jni::HybridClass<WritableNativeArray, ReadableNativeArray> {
 static constexpr const char* kJavaDescriptor = "Lcom/facebook/react/bridge/WritableNativeArray;";

  ...

  static local_ref<jhybriddata> initHybrid(alias_ref<jclass>) {
   return makeCxxInstance();
  }

  ...
}


在創(chuàng)建HybridData(Java)的時候,模板類HybridClass的第一個泛型T,表示的是WritableNativeArray(C++)這個結(jié)構(gòu)體。所以,makeHybridData中的new T(std::forward(args)…)新創(chuàng)建的T就是WritableNativeArray(C++)對象。

繼續(xù)來看makeHybridData方法,參數(shù)cxxPart是剛剛創(chuàng)建的WritableNativeArray對象的指針。里面通過detail::HybridData::create()真正創(chuàng)建了HybridData(Java)和HybridData(C++)對象,并將WritableNativeArray(C++)對象的指針通過setNativePointer方法注入到了HybridData(Java)中。

接下來,看create和setNativePointer兩個方法的細(xì)節(jié),在Hybrid.cpp中:

local_ref<HybridData> HybridData::create() {
 return newInstance();
}
void HybridData::setNativePointer(std::unique_ptr<basehybridclass> new_value) {
 static auto pointerField = getClass()->getField<jlong>("mNativePointer");
 auto* old_value = reinterpret_cast<BaseHybridClass*>(getFieldValue(pointerField));

 if (new_value) {
  ...
 } else if (old_value == 0) {
  return;
 }
 delete old_value;
 ...
 setFieldValue(pointerField, reinterpret_cast<jlong>(new_value.release()));

}

create里面是通過newInstance方式創(chuàng)建了HybridData(Java) 和HybridData(C++)對象,具體細(xì)節(jié)不細(xì)說了,讀者自行去研究facebook的封裝。

HybridData(C++)的setNativePointer方法中的參數(shù)new_value,為WritableNativeArray(C++)對象的指針, 使用reinterpret_cast關(guān)鍵字將其轉(zhuǎn)換成long型,設(shè)置到mNativePointer中。而這里的mNativePointer,就是我們前面談到的HybridData(Java)類的成員變量了!

有一點需要注意的是,保存WritableNativeArray(C++)對象指針的時候,會先獲取原先保存的指針并刪除回收(如果存在的話),主要目的是回收WritableNativeArray(C++)對象的內(nèi)存,調(diào)用的時機是HybridData(Java)的finalize,也就是WritableNativeArray(Java)和HybridData(Java)被虛擬機GC回收的時候,這說明了一點,就是WritableNativeArray(C++)對象實例和WritableNativeArray(Java)對象實例的內(nèi)存釋放是完全同步的,都是交由Java GC來觸發(fā)!

到這里我們稍稍梳理一下。

當(dāng)WritableNativeArray(Java)創(chuàng)建的時候,通過JNI調(diào)用會先創(chuàng)建WritableNativeArray(C++)對象,其后會創(chuàng)建HybridData(Java)和HybridData(C++),同時將WritableNativeArray(C++)的指針保存到HybridData(Java)的mNativePointer成員變量中,最后把HybridData(Java)保存到WritableNativeArray(Java)對象里面。

這樣設(shè)計有一個好處。當(dāng)WritableNativeArray(Java)通過JNI的方式傳遞到C++層時,可以通過保存在其內(nèi)部的HybridData(Java)對象的mNativePointer的值,還原WritableNativeArray(C++)對象。

這個還原過程是通過內(nèi)聯(lián)函數(shù)cthis函數(shù)實現(xiàn)的,代碼在jni/first-party/jni/fbjni/Hybrid.h中:

// Given a *_ref object which refers to a hybrid class, this will reach inside
// of it, find the mHybridData, extract the C++ instance pointer, cast it to
// the appropriate type, and return it.
template <typename T>
inline auto cthis(T jthis) -> decltype(jthis->cthis()) {
 return jthis->cthis();
}
inline T* HybridClass<T, B>::JavaPart::cthis() {
 static auto field =
  HybridClass<T, B>::JavaPart::javaClassStatic()->template getField<detail::HybridData::javaobject>("mHybridData");
 auto hybridData = this->getFieldValue(field);
 ...
 // I'd like to use dynamic_cast here, but -fno-rtti is the default.
 T* value = static_cast<T*>(hybridData->getNativePointer());
 ...
 return value;
};
BaseHybridClass* HybridData::getNativePointer() {
 static auto pointerField = getClass()->getField<jlong>("mNativePointer");
 auto* value = reinterpret_cast<BaseHybridClass*>(getFieldValue(pointerField));
 ...
 return value;
}

先提取出WritableNativeArray(Java)對象的mHybridData,再提取其mNativePointer,最后使用reinterpret_cast還原出WritableNativeArray(C++)對象。而在WritableNativeArray(C++)對象中存儲著所有push的數(shù)據(jù)(定義在其父類NativeArray中),這樣數(shù)據(jù)的提取工作就完成了。

到此,Java傳輸數(shù)據(jù)給C++的場景分析完成,下面我們來研究反向過程。

C++傳輸數(shù)據(jù)給Java的場景,主要是在callNativeModules里面,我們直接來看makeJavaCall方法,在jni\react\jni\OnLoad.cpp中

static void makeJavaCall(JNIEnv* env, ExecutorToken executorToken, jobject callback, const MethodCall& call) {
 if (call.arguments.isNull()) {
  return;
 }

 ...

 auto newArray = ReadableNativeArray::newObjectCxxArgs(std::move(call.arguments));
 env->CallVoidMethod(
   callback,
   gCallbackMethod,
   static_cast<JExecutorTokenHolder*>(executorToken.getPlatformExecutorToken().get())->getJobj(),
   call.moduleId,
   call.methodId,
   newArray.get());
}

call.arguments是一個封裝好的folly::dynamic對象(詳見folly開源庫),通過newObjectCxxArgs方法轉(zhuǎn)換成ReadableNativeArray(C++)對象,實現(xiàn)在jni/first-party/jni/fbjni/Hybrid.h中:

template <typename... Args>
static local_ref<JavaPart> newObjectCxxArgs(Args&&... args) {
  auto hybridData = makeCxxInstance(std::forward<Args>(args)...);
  return JavaPart::newInstance(hybridData);
}
template <typename... Args>
static local_ref<detail::HybridData> makeCxxInstance(Args&&... args) {
 return makeHybridData(std::unique_ptr<T>(new T(std::forward<Args>(args)...)));
}
template<typename JC, typename... Args>
static local_ref<JC> newInstance(Args... args) {
 static auto cls = JC::javaClassStatic();
 static auto constructor = cls->template getConstructor<typename JC::javaobject(Args...)>();
 return cls->newObject(constructor, args...);
}

創(chuàng)建ReadableNativeArray(C++)對象的過程和前面創(chuàng)建WritableNativeArray(C++)對象的過程一模一樣。先創(chuàng)建HybridData(Java)和HybridData(C++),同時將ReadableNativeArray(C++)的指針保存到HybridData(Java)的mNativePointer成員變量中。最后ReadableNativeArray(Java)對象被封裝在JavaPart中(再次用到facebook用JNI創(chuàng)建Java對象的封裝庫),通過get方法獲取到真正的實例。

繼續(xù)來看ReadableNativeArray(Java),位于包com.facebook.react.bridge中:

public class ReadableNativeArray extends NativeArray implements ReadableArray {
  static {
   SoLoader.loadLibrary(ReactBridge.REACT_NATIVE_LIB);
  }

  protected ReadableNativeArray(HybridData hybridData) {
   super(hybridData);
  }

  @Override
  public native int size();
  @Override
  public native boolean isNull(int index);
  @Override
  public native boolean getBoolean(int index);
  @Override
  public native double getDouble(int index);
  @Override
  public native int getInt(int index);
  @Override
  public native String getString(int index);
  @Override
  public native ReadableNativeArray getArray(int index);
  @Override
  public native ReadableNativeMap getMap(int index);
  @Override
  public native ReadableType getType(int index);
}

ReadableNativeArray(Java)同樣也是一個管道,所有數(shù)據(jù)仍然是存在C++層,必須全部通過native本地方法來提取,依賴具有了前面說到的兩個優(yōu)點:減少內(nèi)存和容易回收。

ReadableNativeArray::ReadableNativeArray(folly::dynamic array)
  : HybridBase(std::move(array)) {}

...

jint ReadableNativeArray::getSize() {
 return array.size();
}

jboolean ReadableNativeArray::isNull(jint index) {
 return array.at(index).isNull() ? JNI_TRUE : JNI_FALSE;
}

jboolean ReadableNativeArray::getBoolean(jint index) {
 return array.at(index).getBool() ? JNI_TRUE : JNI_FALSE;
}

jdouble ReadableNativeArray::getDouble(jint index) {
 const folly::dynamic& val = array.at(index);
 if (val.isInt()) {
  return val.getInt();
 }
 return val.getDouble();
}

jint ReadableNativeArray::getInt(jint index) {
 auto integer = array.at(index).getInt();
 ...
 jint javaint = static_cast<jint>(integer);
 ...
 return javaint;
}

const char* ReadableNativeArray::getString(jint index) {
 const folly::dynamic& dyn = array.at(index);
 if (dyn.isNull()) {
  return nullptr;
 }
 return dyn.getString().c_str();
}

ReadableNativeArray::getArray(jint index) {
 auto& elem = array.at(index);
 if (elem.isNull()) {
  return jni::local_ref<ReadableNativeArray::jhybridobject>(nullptr);
 } else {
  return ReadableNativeArray::newObjectCxxArgs(elem);
 }
}

jobject ReadableNativeArray::getMap(jint index) {
 return createReadableNativeMapWithContents(Environment::current(), array.at(index));
}

jobject ReadableNativeArray::getType(jint index) {
 return type::getType(array.at(index).type());
}

void ReadableNativeArray::registerNatives() {
 jni::registerNatives("com/facebook/react/bridge/ReadableNativeArray", {
  makeNativeMethod("size", ReadableNativeArray::getSize),
  makeNativeMethod("isNull", ReadableNativeArray::isNull),
  makeNativeMethod("getBoolean", ReadableNativeArray::getBoolean),
  makeNativeMethod("getDouble", ReadableNativeArray::getDouble),
  makeNativeMethod("getInt", ReadableNativeArray::getInt),
  makeNativeMethod("getString", ReadableNativeArray::getString),
  makeNativeMethod("getArray", ReadableNativeArray::getArray),
  makeNativeMethod("getMap", "(I)Lcom/facebook/react/bridge/ReadableNativeMap;",
           ReadableNativeArray::getMap),
  makeNativeMethod("getType", "(I)Lcom/facebook/react/bridge/ReadableType;",
           ReadableNativeArray::getType),
 });
}

對數(shù)據(jù)的提取,最后仍然是對array對象操作,其是定義在父類NativeArray.h中的,不在贅述。

整個數(shù)據(jù)模型的分析就到此結(jié)束了,總結(jié)一下有以下幾個特點:

1、數(shù)據(jù)只有一份存儲,即在C++中,無論是ReadableNativeArray(Java)還是WritableNativeArray(Java)都只是數(shù)據(jù)存取的管道。

2、ReadableNativeArray和WritableNativeArray在Java層和C++層又都有各自的實例,通過Java層實例的HybridData的mNativePointer作為紐帶鏈接,其存儲的是C++層實例的指針。

3、無論是Java層還是C++層的ReadableNativeArray和WritableNativeArray都是統(tǒng)一由Java GC進行回收管理。

感謝閱讀,希望能幫助到大家,謝謝大家對本站的支持!

相關(guān)文章

最新評論