一般描述:我有两个项目A和B。项目A,必须使用v1版本的L库/API。项目B,必须使用L库/API的v2版本。项目A依赖于项目B(在项目A中,我需要调用B中包含的方法)。
具体描述:项目A实际上是一个机器学习器,它有一组使用旧版本的spark-mllib的算法。我想在项目A中集成XGBOOST-spark算法。
问题是XGBOOST api,特别是: ml.dmlc.xgboost4j.scala.spark.XGBoost.train()方法,需要一个RDD<org.apache.spark.ml.feature.LabeledPoint>。但是org.apache.spark.ml.feature.LabeledPoint只在较新版本的spark-mllib中可用。从项目A(它使用旧版本的spark-mllib),我只能访问一个org.apache.spark.mllib.regression.LabeledPoint.因此,如果不升级项目A的spark-mllib版本,我就无法在项目A中直接集成XGBOOST。
幸运的是,新版本的spark-mllib有一种方法可以将旧的(org.apache.spark.mllib.regression.LabeledPoint) LabeledPoint转换为新的LabeledPoint (org.apache.spark.ml.feature.LabeledPoint)。方法是: org.apache.spark.mllib.regression.LabeledPoint.asML().
所以,问题是:有没有什么聪明的方法可以使用.asML()方法,它只在较新版本的spark中可用,这样我就可以转换LabeledPoint并将其传递给XGBOOST API?
我不熟悉maven是如何处理依赖关系的,但我想到了类似这样的东西:
创建一个使用较新版本的spark-mllib和XGBOOST-API的项目B,其中我们有一个类和一个方法来接收参数(从项目A),将旧的LabeledPoint转换为新的LabeledPoint,调用生成模型的XGBoost.train()方法,然后我们将模型传递回项目A。我们在项目A中导入该类(从项目B),调用它的方法,获取模型,然后我们照常继续我们的业务。
当然,我也试过这么做。但它不起作用。我认为这是因为我们在整个依赖树中只能有一个版本的spark-mllib。由于项目B中的类抛出了java.lang.NoSuchMethodError: org.apache.spark.mllib.regression.LabeledPoint.asML()Lorg/apache/spark/ml/feature/LabeledPoint;,似乎在整个依赖关系树中,我们实际上使用了较旧版本的spark-mllib (这是因为较旧版本更接近依赖关系树的根)。尽管在项目B中我们使用了较新版本的spark-mllib,它提供了asML()方法。
所以,真正的问题是:有没有什么聪明的方法可以做到这一点?而不升级项目A上的spark-mllib版本?升级不是一个可行的选择。项目A很大,如果我升级了那个版本,我几乎把一切都搞砸了。
更新我甚至尝试使用ClassLoader (URLClassLoader),以便直接从spark-mllib_2.11-2.3.0.jar加载类并打印所有可用的方法。代码如下:
URLClassLoader clsLoader = URLClassLoader.newInstance(new URL[] {
new URL("file:///home/myhome/spark-mllib_2.11-2.3.0.jar")
});
Class cls = clsLoader.loadClass("org.apache.spark.mllib.regression.LabeledPoint");
Method[] m = cls.getDeclaredMethods();
for (int i = 0; i < m.length; i++)
System.out.println(m[i].toString());在此项目的.pom文件中,如果添加以下依赖项:
<dependency>
<groupId>org.apache.spark</groupId>
<artifactId>spark-mllib_2.11</artifactId>
<version>2.3.0</version>
</dependency>如果我使用2.3.0版本,方法public org.apache.spark.ml.feature.LabeledPoint org.apache.spark.mllib.regression.LabeledPoint.asML()将显示结果。
但是当我使用spark-mllib的1.6.2版本时,它就不存在了。即使asML()方法在spark-mllib的jar中。这有点奇怪。
发布于 2018-04-25 16:48:26
您可以通过创建项目B的着色依赖项并在项目A中使用它来实现此目的。请参阅此answer以了解maven着色以及如何使用它。
https://stackoverflow.com/questions/50017124
复制相似问题