关于Java通过Runtime调用python代码

Java通过Runtime方法

因为前端跨域和机器访问权限问题,前端访问python代码的获取timelineData数据的接口无法不通过代理的形式直接得到,需要java端来提供一个复写的接口,本来程序已经马上就迁移完成了,怎晓得j在ava端竟然寻不到tensorflow的同构包,无奈,自能在java代码中同时借助python代码来迅速解决该问题了。
  1. 网上给出过很多通过PythonInterpreter来调用python脚本的方案,若果在您的代码中不包含第三方依赖的话,这未尝不是一种比较方便快捷的方案,在这里就不做讨论了。

  2. 当在python脚本中包含第三方依赖时,目前的解决方案是通过Runtime工具执行cmd命令来调用本地python解释器,然后通过在本地安装需要的依赖包并在python脚本中正常导入即可。

  3. 安装tensorflow包步骤(mac通过pip安装,当然也可以通过yum或者rpm安装):

    1.安装pip命令`$ sudo easy_install pip`
    2.建议使用执行python -m pip install -U pip setuptools进行升级
    3.执行安装tensorflow命令:pip install --upgrade tensorflow
    
  4. 代码注意事项:

    1.java代码实例:
    
 String response="需要穿进python中的代码"
 FileUtil.writeToFile(new File("/home/admin/xxx.txt"), response);
                String pythonPath = "/home/admin/python/usr/bin/python2.7";
                String timelineScript = "/home/admin/aop-service/target/xxxx/BOOT-INF/classes/demo.py";//此处为代码被编译打包之后项目中python脚本被存放的位置,注意原文件应该在resource目录下。
                String[] arguments = new String[]{pythonPath, timelineScript};
                //通过python脚本来读取文件并将tensorflow执行timeline转化后重新写入data文件
                Process exec = Runtime.getRuntime().exec(arguments);
                StringBuilder resultAppend = new StringBuilder();
                //等待脚本执行完成
                exec.waitFor();
                //用输入输出流来截取结果
                BufferedReader bufferedReader = FileUtil.readFile("/home/admin/timelineData.txt", "UTF-8");
                String lintTxt;
                while ((lintTxt = bufferedReader.readLine()) != null) {
                    resultAppend.append(lintTxt);

                }
	2.python代码实例:
# -*- coding: utf-8 -*-

import collections
import tensorflow as tf
from google.protobuf import text_format
from tensorflow.python.client import timeline

import json


def analyze_step_stats(self, show_dataflow=True, show_memory=True):
    self._allocate_pids()
    self._assign_lanes()
    self._analyze_tensors(show_memory)
    self._show_compute(show_dataflow)
    if show_memory:
        self._show_memory_counters()
    return StepStatsAnalysis(
        chrome_trace=self._chrome_trace,
        allocator_maximums=self._allocator_maximums)


def generate_chrome_trace_format(self, show_dataflow=True, show_memory=False):
    """Produces a trace in Chrome Trace Format.

    Args:
      show_dataflow: (Optional.) If True, add flow events to the trace
        connecting producers and consumers of tensors.
      show_memory: (Optional.) If True, add object snapshot events to the trace
        showing the sizes and lifetimes of tensors.

    Returns:
      A JSON formatted string in Chrome Trace format.
    """
    step_stats_analysis = self.analyze_step_stats(
        show_dataflow=show_dataflow, show_memory=show_memory)

    return step_stats_analysis.chrome_trace.format_to_string(pretty=True)


a = open('/home/admin/xxx.txt')
response = a.read()
a.close()
response = json.loads(response)
debug_info = response['xxx']
all_meta = []
for line in debug_info.split('\n'):
    if not line.startswith("RUN_METADATA"):
        continue
    space = line.find(' ')
    if space == -1:
        continue
    line = line[space + 1:]
    all_meta.append(line)

if len(all_meta) == 0:
    print ' '
else:
    pb_meta = tf.RunMetadata()
    line_number = 0
    for record in all_meta:
        part_meta = tf.RunMetadata()
        text_format.Merge(record, part_meta)
        for stat in part_meta.step_stats.dev_stats:
            stat.device = str(line_number) + ':' + stat.device
        pb_meta.MergeFrom(part_meta)
        line_number += 1
    tl = timeline.Timeline(pb_meta.step_stats)
    ret = tl.generate_chrome_trace_format()
    b = open('/home/admin/xxx.txt', 'w')
    timelinedata = b.write(ret)
    b.close()


class StepStatsAnalysis(collections.namedtuple(
    'StepStatsAnalysis', ('chrome_trace', 'allocator_maximums'))):
    """Stores the step stats analysis output.

    Parameters:
      chrome_trace: A dict containing the chrome trace analysis.
      allocator_maximums: A dict mapping allocator names to AllocationMaximum.
    """
    pass

	3.本人python代码基本功不太好,稍加评论不要见笑:
在python脚本中依然可以定义需要的函数供被执行的代码调用,但是注意java中利用Runtime调用python解释器时一定要选中对应已安装相关模板的解释器才可以,不然你不会看到任何错误信息但是代码缺却依然执行完成了。	

只有单独通过python解释器执行py脚本才能看到python脚本是否完善,建议一定要先确保自己的python脚本没有问题
5. 当然你也可以通过不利用IO流读写的形式来传入参数和获取python脚本执行结果。可以通过另外一种方式将java端参数传给python脚本:
此处为借鉴

# encoding: utf-8
import sys
from selenium import webdriver

#a即为java传入的参数
def main(a):
    driver = webdriver.Chrome()  # 打开浏览器
    driver.get(a)  # 浏览器打开指定页面


if __name__ == '__main__':
    for i in range(1, len(sys.argv)):
        url = sys.argv[i]
        main(url)

package com.taobao.recommendplatform.solutions.jiayu_test.aop;

import java.io.BufferedReader;
import java.io.InputStreamReader;

public class TestJavaCallPython {

    public static void main(String[] args) {
        try {
            String url = "http://blog.csdn.net/thorny_v/article/details/61417386";
            System.out.println("start;" + url);
            //通过字符串数组的形式向python脚本传入参数,,第一位和第二位为oython解释器的路径和python 脚本路径,后面即为参数,可以随意传递多个参数。
            String[] args1 = new String[]{"python", "/Users/morningrain/IdeaProjects/jcy_test/src/main/resources/demo.py", url};
            Process pr = Runtime.getRuntime().exec(args1);
            BufferedReader in = new BufferedReader(new InputStreamReader(
                    pr.getInputStream()));
            String line;
            while ((line = in.readLine()) != null) {
                System.out.println(line);
            }
            in.close();
            pr.waitFor();
            System.out.println("end");
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

  1. 注意使用第二种方式向python脚本传递参数时,当传入的参数过长时,首先可能会出现java编译问题,其次python解析器也可能无法取得过长的传递参数。
  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值