成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

[譯] 深入對(duì)比數(shù)據(jù)科學(xué)工具箱:Python 和 R 的 C/C++ 實(shí)現(xiàn)

jimhs / 427人閱讀

摘要:另外一個(gè)我們同時(shí)使用兩種語(yǔ)言的原因是已有的統(tǒng)計(jì)學(xué)工具與包。對(duì)另一些為讀者寫數(shù)據(jù)科學(xué)工具的人來(lái)說(shuō)他們從一開(kāi)始就考慮了這些跨語(yǔ)言。和實(shí)際上是用實(shí)現(xiàn)的這是條阻力最小的路徑。無(wú)論是哪個(gè)贏得這場(chǎng)語(yǔ)言戰(zhàn)爭(zhēng),和都將保持在數(shù)據(jù)科學(xué)屆的地位。

概述

幾周前,我有幸在 Scipy 大會(huì)上發(fā)表了 Civis如何使用Python和R的演講。為什么要在一個(gè)Python大會(huì)上大談R呢?這是要挑起一個(gè)Python和R語(yǔ)言的一場(chǎng)戰(zhàn)爭(zhēng)嗎?不是的!討論哪個(gè)語(yǔ)言比較好簡(jiǎn)直是浪費(fèi)時(shí)間。在 Civis,我們很愉快地同時(shí)使用這兩種語(yǔ)言,不僅僅是在我們?nèi)粘9ぷ髦薪鉀Q數(shù)據(jù)科學(xué)問(wèn)題,也用它們來(lái)寫一些其他工具。下面是我在SciPy 大會(huì)上的一些討論。

問(wèn)題現(xiàn)狀

我們 Civis 的同事有著十分不同的學(xué)術(shù)背景。我效力的研發(fā)團(tuán)隊(duì)有一個(gè)物理學(xué)家、一個(gè)經(jīng)濟(jì)學(xué)家、兩個(gè)統(tǒng)計(jì)學(xué)家以及一位土木工程師組成。在 Civis,每個(gè)人在數(shù)據(jù)科學(xué)上都會(huì)做一些不同內(nèi)容的工作,有的領(lǐng)域是R比較流行,有的領(lǐng)域是Python比較流行,還有的一些是Matlab。在這種場(chǎng)景下只支持一種語(yǔ)言并不是一個(gè)明智的選擇。遷移到一門新語(yǔ)言上會(huì)花費(fèi)許多時(shí)間,拋開(kāi)在學(xué)院或者業(yè)界多年的技能回報(bào),允許人們使用它們所熟悉的工具可以確保大家有更高的生成效率。

另外一個(gè)我們同時(shí)使用兩種語(yǔ)言的原因是已有的統(tǒng)計(jì)學(xué)工具與包。在解決數(shù)據(jù)科學(xué)問(wèn)題上,我們經(jīng)常遇到在某些特定管道上需要某一種特定語(yǔ)言。我們的調(diào)研管道是一個(gè)很好的例子。確保隨機(jī)樣本具有全集代表性是需要一個(gè)被稱為 raking 的過(guò)程的,傳統(tǒng)上,Python 在社會(huì)科學(xué)上并不流行,因此我們只會(huì)用R來(lái)完成這件事情。當(dāng)然調(diào)查也包括了QA的全文檢索,在某種程度上來(lái)說(shuō)R在NLP社區(qū)上并不是很流行,因此這個(gè)部分將會(huì)由Python來(lái)完成。而分析調(diào)查數(shù)據(jù)只是我們?cè)贑ivis解決問(wèn)題的一個(gè)小步驟。

結(jié)合許多不同的語(yǔ)言來(lái)實(shí)現(xiàn)工作流是具有挑戰(zhàn)性的。數(shù)據(jù)科學(xué)平臺(tái)幫助我們可以提交一連串任務(wù)節(jié)點(diǎn),然后交由基礎(chǔ)設(shè)施負(fù)責(zé)獨(dú)立調(diào)用每個(gè)任務(wù)節(jié)點(diǎn),且前后不依賴。但是這并不是一個(gè)十分理想的情況。原因有二,其一,這樣做整個(gè)任務(wù)就顯得破碎化,稍有修改某個(gè)任務(wù),往往會(huì)導(dǎo)致全局失敗,而且任何人在這個(gè)分布式系統(tǒng)中所做的工作都只了解局部情況,而不知道全局情況。第二,這樣做并不高效。在兩個(gè)語(yǔ)言中切換通常需要將數(shù)據(jù)以特定格式加載到磁盤上(通常最壞的情況是csv格式)。這樣不僅僅是解析成本比較高,而且還會(huì)丟失一些類型信息。

解決方案

我概述了在Civis遇到的種種問(wèn)題,但是到底什么是理想的狀態(tài)呢?最完美的解決方案是我們可以無(wú)縫切換工具和語(yǔ)言。許多熟悉Python的人喜歡用Python做數(shù)據(jù)分析,R也是類似的。事實(shí)證明這是完全有可能實(shí)現(xiàn),有相當(dāng)數(shù)量的項(xiàng)目已經(jīng)開(kāi)始作為跨語(yǔ)言工具:TensorFlow, XGBoost, 和 Stan 都在Civis被廣泛運(yùn)用。移植或安利一個(gè)已有的工具也是可能的,我們已經(jīng)成功地完成了glmnetR包的安利。

對(duì)另一些為讀者寫數(shù)據(jù)科學(xué)工具的人來(lái)說(shuō),他們從一開(kāi)始就考慮了這些跨語(yǔ)言。有一些方法可以做到這一點(diǎn),但我個(gè)人最喜歡的是用C語(yǔ)言來(lái)寫底層,然后使用各自的Python和R C api做一些綁定/封裝。Python和R實(shí)際上是用C實(shí)現(xiàn)的,這是條阻力最小的路徑。C是一門古老語(yǔ)言,C語(yǔ)言社區(qū)已經(jīng)演進(jìn)出了一些強(qiáng)大的工具鏈?;逎木幾g器錯(cuò)誤消息已經(jīng)成為了過(guò)去時(shí),GCC和Clang(最流行的編譯器)給友善的消息反饋(Clang網(wǎng)站可以看到栗子)。現(xiàn)在還有各種各樣的“消毒液”來(lái)輔助捕獲內(nèi)存泄漏等常見(jiàn)錯(cuò)誤或未定義的行為(llvm文檔)。

案例

下面我們通過(guò)一個(gè)小例子,用C編寫一個(gè)函數(shù),使這可調(diào)用的Python和R。代碼以及幻燈片從我的GitHub上可以找到。

Python

我們將下面的Python函數(shù)轉(zhuǎn)換為C:

def tally(s):
    total = 0
    for elm in s:
        total += elm
    return total
C

這是相同的功能用C實(shí)現(xiàn):

#include 

double tally(double *s, size_t n) {
    double total = 0;
    for (size_t i = 0; i < n; i++) {
        total += s[i];
    }
    return total;
}

注意到它看起來(lái)并不是都不同的Python函數(shù)。當(dāng)然,除了有一些類型注解和額外的語(yǔ)法噪音大括號(hào)外,我們還必須跟蹤數(shù)組的長(zhǎng)度,但整體邏輯是一樣的。

接下來(lái),我們需要實(shí)現(xiàn)一個(gè)Python綁定,允許用戶調(diào)用這個(gè)函數(shù)就像任何其他Python函數(shù)。

Cython
#include 
#include "Python.h"
#include "tally.h"

static PyObject *tally_(PyObject *self, PyObject *args) {
    PyObject *buf;
    if (!PyArg_ParseTuple(args, "O", &buf)) {
        return NULL;
    }

    Py_buffer view;
    int buf_flags = PyBUF_ANY_CONTIGUOUS | PyBUF_FORMAT;
    if (PyObject_GetBuffer(buf, &view, buf_flags) == -1) {
        return NULL;
    }
    
    if (strcmp(view.format,"d") != 0) {
        PyErr_SetString(PyExc_TypeError, "we only take floats :(");
        PyBuffer_Release(&view);
        return NULL;
    }

    double result = tally(view.buf, view.shape[0]);
    PyBuffer_Release(&view);
    return Py_BuildValue("d", result);
}

static PyMethodDef MethodTable[] = {
    {"tally", &tally_, METH_VARARGS, "Compute the sum of an array"}, 
    { NULL, NULL, 0, NULL}
};

static struct PyModuleDef tally_module = {
    .m_base = PyModuleDef_HEAD_INIT,
    .m_name = "tally_",
    .m_size = -1,
    .m_methods = MethodTable
};


PyMODINIT_FUNC PyInit_tally_(void) {
    return PyModule_Create(&tally_module);
}

這里有很多實(shí)現(xiàn)的方法,但大多數(shù)只是Python模塊的一部分樣板代碼。
在最上面,我們定義了一個(gè)函數(shù),它接受一個(gè)Python對(duì)象,并且檢查這是一個(gè)適當(dāng)類型的數(shù)組,再調(diào)用我們的計(jì)數(shù)功能,然后返回結(jié)果。其余的代碼模塊定義,告訴Python解釋器我們計(jì)數(shù)功能的名稱和它的參數(shù)類型。

R

R的過(guò)程非常相似,但是更加簡(jiǎn)潔:

#include 
#include 
#include 
#include "tally.h"

SEXP tally_(SEXP x_) {
  double *x = REAL(x_);
  int n = length(x_);
  
  SEXP out = PROTECT(allocVector(REALSXP, 1));
  REAL(out)[0] = tally(x, n);
  UNPROTECT(1);
  
  return out;
}

static R_CallMethodDef callMethods[] = {
  {"tally_", (DL_FUNC)&tally_, 1},
  {NULL, NULL, 0}
};

void R_init_tallyR(DllInfo *info) {
  R_registerRoutines(info, NULL, callMethods, NULL, NULL);
}

這里需要的代碼量顯著減少,因?yàn)镽和Python類型系統(tǒng)有所不同,沒(méi)有真正標(biāo)量類型,所以我們不需要做相同級(jí)別的檢驗(yàn)/驗(yàn)證用戶輸入我們?cè)谏厦娴腜ython示例。剩下的代碼大致相同,我們定義一個(gè)組函數(shù)可在R編譯。

總結(jié)

一個(gè)真實(shí)世界的例子一定會(huì)更加復(fù)雜,但整個(gè)過(guò)程并不是那么困難。在編寫跨語(yǔ)言工具時(shí)有幾件事要記住:

如果你打算在兩者之間共享函數(shù)就不要依賴宿主語(yǔ)言的api(R或Python)代碼。

使用錯(cuò)誤碼來(lái)傳遞異常提示,不要直接調(diào)用退出或者在宿主語(yǔ)言里面才處理異常。

最好用宿主語(yǔ)言負(fù)責(zé)內(nèi)存分配和重分配,這意味著你的C/C++代碼應(yīng)該要略過(guò)預(yù)先分配的內(nèi)存和輸出過(guò)程。

相信編譯器,你也應(yīng)該重視編譯器的錯(cuò)誤和警告。如果代碼在編譯時(shí)有警告那代碼就不算寫完。

無(wú)論是哪個(gè)“贏得”這場(chǎng)語(yǔ)言戰(zhàn)爭(zhēng),Python和R都將保持在數(shù)據(jù)科學(xué)屆的地位。這意味著為工具開(kāi)發(fā)者不能忽視的另外一門語(yǔ)言,構(gòu)建有用的工具就得保證這兩種語(yǔ)言都可以使用。一個(gè)簡(jiǎn)單的方式是用C或c++編寫大量代碼,然后用 C 的 API的為兩種語(yǔ)言提供封裝。

參考資料

GitHub Scipy 2016

Linkedin: Python or R?

原作者:Bill Lattner 翻譯:Harry Zhu
英文原文地址:Forget Python vs. R: how they can work together

作為分享主義者(sharism),本人所有互聯(lián)網(wǎng)發(fā)布的圖文均遵從CC版權(quán),轉(zhuǎn)載請(qǐng)保留作者信息并注明作者 Harry Zhu 的 FinanceR專欄:https://segmentfault.com/blog...,如果涉及源代碼請(qǐng)注明GitHub地址:https://github.com/harryprince。微信號(hào): harryzhustudio
商業(yè)使用請(qǐng)聯(lián)系作者。

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/38123.html

相關(guān)文章

  • [原]深入對(duì)比數(shù)據(jù)科學(xué)具箱PythonR之爭(zhēng)[2016版]

    摘要:概述在真實(shí)的數(shù)據(jù)科學(xué)世界里,我們會(huì)有兩個(gè)極端,一個(gè)是業(yè)務(wù),一個(gè)是工程。偏向業(yè)務(wù)的數(shù)據(jù)科學(xué)被稱為數(shù)據(jù)分析,也就是型數(shù)據(jù)科學(xué)。所以說(shuō),同時(shí)學(xué)會(huì)和這兩把刷子才是數(shù)據(jù)科學(xué)的王道。 showImg(https://segmentfault.com/img/bVAgki?w=980&h=596); 概述 在真實(shí)的數(shù)據(jù)科學(xué)世界里,我們會(huì)有兩個(gè)極端,一個(gè)是業(yè)務(wù),一個(gè)是工程。偏向業(yè)務(wù)的數(shù)據(jù)科學(xué)被稱為數(shù)據(jù)...

    whidy 評(píng)論0 收藏0
  • [原] 深入對(duì)比數(shù)據(jù)科學(xué)具箱Python R 異常處理機(jī)制

    摘要:對(duì)于異常機(jī)制的合理運(yùn)用是直接關(guān)系到碼農(nóng)飯碗的事情所以,本文將具體介紹一下和的異常處理機(jī)制,闡明二者在異常處理機(jī)制上的異同。下面將具體介紹二者的異常處理機(jī)制。 概述 showImg(https://segmentfault.com/img/remote/1460000006760426); 異常處理,是編程語(yǔ)言或計(jì)算機(jī)硬件里的一種機(jī)制,用于處理軟件或信息系統(tǒng)中出現(xiàn)的異常狀況(即超出程序正...

    FreeZinG 評(píng)論0 收藏0
  • [原]深入對(duì)比數(shù)據(jù)科學(xué)具箱PythonR Web 編輯器

    摘要:概述工欲善其事必先利其器,如果現(xiàn)在要評(píng)選數(shù)據(jù)科學(xué)中最好用的編輯器注意一定是可以通過(guò)訪問(wèn)的,和一定是角逐的最大熱門,正確使用編輯器可以很大地提升我們的工作效率。 概述 showImg(https://segmentfault.com/img/bVAdol); 工欲善其事必先利其器,如果現(xiàn)在要評(píng)選數(shù)據(jù)科學(xué)中最好用的Web 編輯器(注意一定是可以通過(guò)Web訪問(wèn)的),RStudio和Jupyt...

    RobinQu 評(píng)論0 收藏0
  • [原]深入對(duì)比數(shù)據(jù)科學(xué)具箱PythonR 非結(jié)構(gòu)化數(shù)據(jù)結(jié)構(gòu)化

    摘要:則在讀取數(shù)據(jù)時(shí)將兩個(gè)中文字段混淆成了一個(gè)字段,導(dǎo)致整個(gè)數(shù)據(jù)結(jié)構(gòu)錯(cuò)亂。三條路子全軍覆沒(méi),這讓我情何以堪,好在使用的經(jīng)驗(yàn)頗豐,通過(guò)中文的轉(zhuǎn)換和切割就輕松解決了這個(gè)問(wèn)題。 概述 showImg(https://segmentfault.com/img/bVylLL); 在現(xiàn)實(shí)場(chǎng)景中,由于數(shù)據(jù)來(lái)源的異構(gòu),數(shù)據(jù)源的格式往往是難以統(tǒng)一的,這就導(dǎo)致大量具有價(jià)值的數(shù)據(jù)通常是以非結(jié)構(gòu)化的形式聚合在一起的...

    leiyi 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

jimhs

|高級(jí)講師

TA的文章

閱讀更多
最新活動(dòng)
閱讀需要支付1元查看
<