電子發(fā)燒友App

硬聲App

0
  • 聊天消息
  • 系統(tǒng)消息
  • 評(píng)論與回復(fù)
登錄后你可以
  • 下載海量資料
  • 學(xué)習(xí)在線課程
  • 觀看技術(shù)視頻
  • 寫文章/發(fā)帖/加入社區(qū)
會(huì)員中心
創(chuàng)作中心

完善資料讓更多小伙伴認(rèn)識(shí)你,還能領(lǐng)取20積分哦,立即完善>

3天內(nèi)不再提示
創(chuàng)作
電子發(fā)燒友網(wǎng)>電子資料下載>電子資料>野生動(dòng)物探測器開源分享

野生動(dòng)物探測器開源分享

2022-10-31 | zip | 0.28 MB | 次下載 | 免費(fèi)

資料介紹

描述

在科羅拉多州和其他擁有大量野生動(dòng)物種群的州,人類與野生動(dòng)物之間的沖突并不少見(城鎮(zhèn)中的熊和駝鹿、涉及麋鹿的交通事故等)

我決定通過創(chuàng)建一個(gè)檢測運(yùn)動(dòng)、拍照并使用機(jī)器學(xué)習(xí)算法分析它以采取某種行動(dòng)(嚇跑它、點(diǎn)亮標(biāo)志、通知當(dāng)局)。此外,該設(shè)備跟蹤環(huán)境數(shù)據(jù),以幫助研究人員跟蹤可能導(dǎo)致更多野生動(dòng)物遭遇的遷徙模式和條件,它還檢測野火以防止不必要的破壞。

?
pYYBAGNY5nuACeNLAA9XERvSk2Y998.jpg
檢測裝置

分類

該項(xiàng)目的主要重點(diǎn)是機(jī)器學(xué)習(xí)野生動(dòng)物分類。我通過訓(xùn)練 TensorFlow 來使用來自 Google 圖片的數(shù)據(jù)來識(shí)別四種特定的動(dòng)物物種,從而實(shí)現(xiàn)了這一點(diǎn)。所有的初始訓(xùn)練都是在計(jì)算機(jī)上使用為 TensorFlow 和一千多張野生動(dòng)物圖片預(yù)先配置的 docker 機(jī)器圖像完成的。一旦 TensorFlow 被訓(xùn)練,圖形文件被優(yōu)化以在移動(dòng)設(shè)備上運(yùn)行,然后它可以被用來在 Android Things 設(shè)備上運(yùn)行,方法是拍攝一張圖像,調(diào)整它的大小,然后通過 TensorFlow 運(yùn)行它以確定該圖像是否包含一個(gè)我們預(yù)先訓(xùn)練的分類,以及到什么置信水平。

一旦確定了動(dòng)物,就必須對(duì)這些數(shù)據(jù)進(jìn)行處理。根據(jù)您的情況,您可以使用額外的硬件來閃光、播放聲音或做任何其他事情。對(duì)于這個(gè)原型,我將 Android Things 連接到 Firebase 后端,以便簡單地保存圖像和分類信息

?
poYBAGNY5oiANoSQAAAvK5SdqaE792.jpg
設(shè)備拍攝的圖像
?

?

?
pYYBAGNY5oyAAc4yAACCU3dURqw296.png
Firebase 上保存的檢測結(jié)果
?

將信息存儲(chǔ)在 Firebase 上后,您可以創(chuàng)建一個(gè)輔助應(yīng)用程序來接收有關(guān)動(dòng)物存在的通知,或者只是存儲(chǔ)該數(shù)據(jù)以用于研究目的。

此外,如果您希望無需檢查 Firebase 即可看到結(jié)果,您可以在此項(xiàng)目中添加 LCD 屏幕。您可以在此處找到 Gautier Mechling為 1601 系列 LCD 屏幕提供的易于使用的驅(qū)動(dòng)程序。

創(chuàng)建 TensorFlow 分類文件

您要做的第一件事是確保 TensorFlow 在您的計(jì)算機(jī)上并且可以正常工作。這可能相當(dāng)復(fù)雜,我發(fā)現(xiàn)在生成訓(xùn)練文件的整個(gè)過程中使其正常工作的最簡單方法是安裝和使用Docker。該程序?qū)⒃试S您在計(jì)算機(jī)上運(yùn)行為 TensorFlow 預(yù)配置的虛擬機(jī)。

一旦你安裝了 Docker 并讓它在你的計(jì)算機(jī)上運(yùn)行,??你應(yīng)該打開它的首選項(xiàng)并為你的虛擬機(jī)設(shè)置內(nèi)存使用。我將我的內(nèi)存設(shè)置為使用 7 GB 內(nèi)存,這可能超出了您的需要,但我花了幾天時(shí)間試圖讓 TensorFlow 正確創(chuàng)建所需的訓(xùn)練圖表而不會(huì)崩潰,然后我才意識(shí)到虛擬機(jī)內(nèi)存不足。

?
poYBAGNY5o-ASVk0AAB1jm9RC_8529.jpg
?

一旦你安裝了 Docker 并在你的機(jī)器上啟動(dòng)它,你需要從終端運(yùn)行它并下載一個(gè)鏡像。對(duì)于此示例,我在 macOS 下運(yùn)行,因此對(duì)于您的平臺(tái),命令可能會(huì)有所不同。

docker run -it -v $HOME/tf_files:/tf_files gcr.io/tensorflow/tensorflow:latest-develcd /tensorflowgit pullgit checkout v1.0.1

當(dāng)一切都完成設(shè)置后,您應(yīng)該在終端中出現(xiàn)如下提示:

root@1643721c503b:/tensorflow#

此時(shí),您需要一組圖像來訓(xùn)練 TensorFlow。我使用Fatkun Batch Download Image Chrome 插件從 Google 搜索中批量下載返回的圖像。安裝插件后,您可以搜索要分類的任何內(nèi)容并開始選擇要保存的圖像。

?
pYYBAGNY5pGAD78TAADRvcovjy0663.jpg
?

為了使命名更容易,您可能還需要進(jìn)入“更多選項(xiàng)”部分,讓插件在下載圖像時(shí)重命名它們。

?
pYYBAGNY5pOAEku6AAAkpOJz1mM886.jpg
?

接下來,您需要將正在使用的圖像移動(dòng)到主目錄下的tf_files文件夾中,這是我們?cè)诔跏蓟?docker 機(jī)器時(shí)創(chuàng)建的文件夾。對(duì)于此示例,我的圖像目錄稱為TensorFlowTrainingImages 每個(gè)可分類項(xiàng)目都應(yīng)該在該目錄中有自己的文件夾,如下所示。

?
poYBAGNY5paABo04AAA86IZJAMs568.jpg
?

設(shè)置好目錄后,您可以從 Docker 終端使用以下命令開始重新訓(xùn)練:

python tensorflow/examples/image_retraining/retrain.py \  
--bottleneck_dir=/tf_files/bottlenecks \  
--how_many_training_steps 3000 \  
--model_dir=/tf_files/inception \  
--output_graph=/tf_files/graph.pb \  
--output_labels=/tf_files/labels.txt \  
--image_dir /tf_files/TensorFlowTrainingImages

上面的命令會(huì)生成bottlenecks ,本質(zhì)上是最終分類數(shù)據(jù)傳遞使用的數(shù)據(jù),以及用于分類的圖形和標(biāo)簽文件。

從現(xiàn)在開始,我們使用 TensorFlow 運(yùn)行的操作可能需要幾分鐘到一個(gè)多小時(shí),具體取決于您計(jì)算機(jī)的速度。當(dāng)重新訓(xùn)練命令運(yùn)行時(shí),您應(yīng)該會(huì)在終端中看到很多類似于以下內(nèi)容的輸出:

Step 130: Train accuracy = 95.0%2017-04-12 18:21:28.495779: 
Step 130: Cross entropy = 0.2503392017-04-12 18:21:28.748928: 
Step 130: Validation accuracy = 92.0% (N=100) 

生成瓶頸后,您將擁有一個(gè)graph.pb文件和一個(gè)代表您的數(shù)據(jù)的labels.txt文件。雖然這些格式在您的計(jì)算機(jī)上運(yùn)行分類時(shí)效果很好,但它們?cè)诜湃?Android 應(yīng)用程序時(shí)往往不起作用。您將需要優(yōu)化它們。

首先運(yùn)行/configure 命令。接受所有默認(rèn)值。

配置完成后,運(yùn)行以下命令來設(shè)置優(yōu)化工具。這一步在我的機(jī)器上完成了大約一個(gè)小時(shí)。

bazel build tensorflow/python/tools:optimize_for_inference

構(gòu)建優(yōu)化工具后,您可以使用它通過 bazel 優(yōu)化您的圖形文件。

bazel-bin/tensorflow/python/tools/optimize_for_inference \  
--input=/tf_files/graph.pb \  
--output=/tf_files/optimized_graph.pb \  
--input_names=Mul \  
--output_names=final_result

現(xiàn)在您的優(yōu)化圖已經(jīng)生成,您可以在您的主目錄的tf_files文件夾中找到它和您的標(biāo)簽。

?
pYYBAGNY5piAT5fUAAAwf88zCwo339.jpg
?

一旦你有了優(yōu)化的圖表,你就可以將它包含在你的 Android Things 項(xiàng)目中以與之交互。如果您查看該項(xiàng)目的源代碼,您可以看到使用 Camera2 API 獲取圖像并將其傳遞給TensorFlowImageClassifier.java進(jìn)行分類的 Java 代碼。您還可以找到將分類圖像上傳到 Firebase 的代碼,如下所示

private void uploadAnimal(Bitmap bitmap, final Detection detectedAnimal) { 
   ByteArrayOutputStream outputStream = new ByteArrayOutputStream(); 
   bitmap.compress(Bitmap.CompressFormat.JPEG, 100, outputStream); 
   byte[] data = outputStream.toByteArray(); 
   FirebaseStorage storage = FirebaseStorage.getInstance(); 
   StorageReference storageReference = storage.getReferenceFromUrl( 
   	FIREBASE_STORAGE_URL).child(System.currentTimeMillis() + ".jpg"); 
   UploadTask uploadTask = storageReference.putBytes(data); 
   uploadTask.addOnFailureListener(new OnFailureListener() { 
       @Override 
       public void onFailure(@NonNull Exception exception) { 
       } 
   }).addOnSuccessListener(new OnSuccessListener() { 
       @Override 
       public void onSuccess(UploadTask.TaskSnapshot taskSnapshot) { 
           handleNotificationForImage(taskSnapshot.getDownloadUrl(), 
                                      detectedAnimal); 
       } 
   }); 
} 

環(huán)境傳感器

雖然能夠識(shí)別野生動(dòng)物很棒,但這里有機(jī)會(huì)做更多的事情。如果這些設(shè)備之一設(shè)置在荒野中,您還可以添加傳感器來保存天氣信息并將其報(bào)告給您的后端。對(duì)于我的原型,我包括了一個(gè)濕度傳感器、溫度和壓力傳感器、一個(gè)火焰探測器(理論上當(dāng)周圍沒有人時(shí)通知某人野火)、一個(gè)空氣質(zhì)量傳感器和一個(gè)紫外線傳感器。其中一些在附加到 Android Things 方面有其獨(dú)特的挑戰(zhàn),我將在下面介紹。

數(shù)字傳感器

連接到野生動(dòng)物探測器的最簡單的傳感器是火焰探測器和運(yùn)動(dòng)探測器。這些傳感器在低電平空閑,但在檢測到火焰或運(yùn)動(dòng)時(shí)切換到高電平。使用 Android Things 的外圍 I/O API,這些傳感器是最容易支持的,因?yàn)樵O(shè)備只需要監(jiān)聽狀態(tài)的變化。

對(duì) HC SR501 和火焰探測器的支持都遵循這個(gè)類的模式

@SuppressWarnings({"unused", "WeakerAccess"})
public class HCSR501 implements AutoCloseable {
   public enum State {
       STATE_HIGH,
       STATE_LOW;
   }
   public interface OnMotionDetectedEventListener {
       void onMotionDetectedEvent(State state);
   }
   private Gpio mMotionDetectorGpio;
   private OnMotionDetectedEventListener mOnMotionDetectedEventListener;
   private boolean mLastState;
   public HCSR501(String pin) throws IOException {
       PeripheralManagerService pioService = new PeripheralManagerService();
       Gpio HCSR501Gpio = pioService.openGpio(pin);
       try {
           connect(HCSR501Gpio);
       } catch( IOException | RuntimeException e ) {
           close();
           throw e;
       }
   }
   private void connect(Gpio HCSR501Gpio) throws IOException {
       mMotionDetectorGpio = HCSR501Gpio;
       mMotionDetectorGpio.setDirection(Gpio.DIRECTION_IN);
       mMotionDetectorGpio.setEdgeTriggerType(Gpio.EDGE_BOTH);
       mLastState = mMotionDetectorGpio.getValue();
       mMotionDetectorGpio.setActiveType(mLastState ? Gpio.ACTIVE_HIGH : Gpio.ACTIVE_LOW);
       mMotionDetectorGpio.registerGpioCallback(mInterruptCallback);
   }
   private void performMotionEvent(State state) {
       if( mOnMotionDetectedEventListener != null ) {
           mOnMotionDetectedEventListener.onMotionDetectedEvent(state);
       }
   }
   private GpioCallback mInterruptCallback = new GpioCallback() {
       @Override
       public boolean onGpioEdge(Gpio gpio) {
           try {
               if( gpio.getValue() != mLastState ) {
                   mLastState = gpio.getValue();
                   performMotionEvent(mLastState ? State.STATE_HIGH : State.STATE_LOW);
               }
           } catch( IOException e ) {
           }
           return true;
       }
   };
   public void setOnMotionDetectedEventListener(OnMotionDetectedEventListener listener) {
       mOnMotionDetectedEventListener = listener;
   }
   @Override
   public void close() throws IOException {
       mOnMotionDetectedEventListener = null;
       if (mMotionDetectorGpio != null) {
           mMotionDetectorGpio.unregisterGpioCallback(mInterruptCallback);
           try {
               mMotionDetectorGpio.close();
           } finally {
               mMotionDetectorGpio = null;
           }
       }
   }
}

模擬傳感器

Android Things 的模擬傳感器有點(diǎn)棘手。雖然設(shè)備可能具有板載模數(shù)轉(zhuǎn)換器 (ADC),但它并未在 Android Things 平臺(tái)上啟用。為了解決這個(gè)問題,我使用了 MCP3008 ADC 芯片來讀取模擬輸入并將其轉(zhuǎn)換為可以在 Android Things 板上讀取的 int。這是通過一種快速而骯臟的“bit banged”方法完成的,因此您可以更改引腳以匹配您可用的任何內(nèi)容。使用 ADC,我能夠添加對(duì)空氣質(zhì)量傳感器和紫外線傳感器的支持。以下代碼是我用于 MCP3008 的代碼,并且在我使用過的多個(gè) Android Things 項(xiàng)目中被證明是有價(jià)值的。

public class MCP3008 {
   private final String csPin;
   private final String clockPin;
   private final String mosiPin;
   private final String misoPin;
   private Gpio mCsPin;
   private Gpio mClockPin;
   private Gpio mMosiPin;
   private Gpio mMisoPin;
   public MCP3008(String csPin, String clockPin, String mosiPin, String misoPin) {
       this.csPin = csPin;
       this.clockPin = clockPin;
       this.mosiPin = mosiPin;
       this.misoPin = misoPin;
   }
   public void register() throws IOException {
       PeripheralManagerService service = new PeripheralManagerService();
       mClockPin = service.openGpio(clockPin);
       mCsPin = service.openGpio(csPin);
       mMosiPin = service.openGpio(mosiPin);
       mMisoPin = service.openGpio(misoPin);
       mClockPin.setDirection(Gpio.DIRECTION_OUT_INITIALLY_LOW);
       mCsPin.setDirection(Gpio.DIRECTION_OUT_INITIALLY_LOW);
       mMosiPin.setDirection(Gpio.DIRECTION_OUT_INITIALLY_LOW);
       mMisoPin.setDirection(Gpio.DIRECTION_IN);
   }
   public int readAdc(int channel) throws IOException {
       if( channel < 0 || channel > 7 ) {
           throw new IOException("ADC channel must be between 0 and 7");
       }
       initReadState();
       initChannelSelect(channel);
       return getValueFromSelectedChannel();
   }
   private int getValueFromSelectedChannel() throws IOException {
       int value = 0x0;
       for( int i = 0; i < 12; i++ ) {
           toggleClock();
           value <<= 0x1;
           if( mMisoPin.getValue() ) {
               value |= 0x1;
           }
       }
       mCsPin.setValue(true);
       value >>= 0x1; // first bit is 'null', so drop it
       return value;
   }
   private void initReadState() throws IOException {
       mCsPin.setValue(true);
       mClockPin.setValue(false);
       mCsPin.setValue(false);
   }
   private void initChannelSelect(int channel) throws IOException {
       int commandout = channel;
       commandout |= 0x18; // start bit + single-ended bit
       commandout <<= 0x3; // we only need to send 5 bits
       for( int i = 0; i < 5; i++ ) {
           if ( ( commandout & 0x80 ) != 0x0 ) {
               mMosiPin.setValue(true);
           } else {
               mMosiPin.setValue(false);
           }
           commandout <<= 0x1;
           toggleClock();
       }
   }
   private void toggleClock() throws IOException {
       mClockPin.setValue(true);
       mClockPin.setValue(false);
   }
   public void unregister() {
       if( mCsPin != null ) {
           try {
               mCsPin.close();
           } catch( IOException ignore ) {
               // do nothing
           }
       }
       if( mClockPin != null ) {
           try {
               mClockPin.close();
           } catch( IOException ignore ) {
               // do nothing
           }
       }
       if( mMisoPin != null ) {
           try {
               mMisoPin.close();
           } catch( IOException ignore ) {
               // do nothing
           }
       }
       if( mMosiPin != null ) {
           try {
               mMosiPin.close();
           } catch( IOException ignore ) {
               // do nothing
           }
       }
   }
}

不支持的硬件

不幸的是,DHT11 濕度傳感器使用以納秒為間隔觸發(fā)的信號(hào)協(xié)議,但 Android 平臺(tái)僅支持低至毫秒。因此,Android Things 無法直接支持 DHT11。但是,有一種解決方法。使用帶有 Arduino 的 ATMega328p,我能夠?qū)⑿畔?DHT11 讀取到 Arduino 芯片,并使用 I2C 將該信息發(fā)送到 Android Things 設(shè)備。

?
pYYBAGNY5p2AKUg3AAA9Zo7Lgiw391.png
?

您可以通過在 Android 中打開與該地址的連接來使用自定義地址讀取 I2C

PeripheralManagerService service = new PeripheralManagerService();
mHumidity = service.openI2cDevice(BoardDefaults.getHumidityI2cBus(), 0x08);

在上面的示例中,我們使用的自定義地址是8 在 ATMega328p 上運(yùn)行的 Arduino 代碼中,您可以將該地址與 Wire 庫一起使用。

#import 
#include 
 
dht11 DHT11;
 
#define DHT11PIN 13
 
uint8_t humidity;
 
void setup() {
 Wire.begin(8);                // join i2c bus with address #8
 Wire.onRequest(requestEvent); // register event
}
 
void loop() {
 int chk = DHT11.read(DHT11PIN);
 humidity = DHT11.humidity;
 delay(1000);
}
 
void requestEvent() {
 Wire.write(humidity);
}

預(yù)先編寫的驅(qū)動(dòng)程序

雖然添加對(duì)數(shù)字 I/O 的支持很容易,但還有一件事更容易:使用已經(jīng)編寫的代碼。對(duì)于 BMP280,我能夠從 Google 的官方驅(qū)動(dòng)程序庫中引入一個(gè)預(yù)先編寫的驅(qū)動(dòng)程序,讓我無需太多工作或時(shí)間就可以從該環(huán)境傳感器讀取信息。您可以在此處找到 Google 預(yù)先編寫的示例,因?yàn)槠渲杏幸恍┛赡軐?duì)您使用 Android Things 組合在一起的任何項(xiàng)目有用。這些驅(qū)動(dòng)程序很容易進(jìn)入您的項(xiàng)目,就像將它們添加到您的 gradle 依賴項(xiàng)中一樣

dependencies {
   compile 'com.google.android.things.contrib:driver-bmx280:0.2'
   provided 'com.google.android.things:androidthings:0.4-devpreview'
}

對(duì)于這個(gè)項(xiàng)目,我還使用 GPS 驅(qū)動(dòng)程序?qū)⑽恢脭?shù)據(jù)添加到 Firebase,盡管您可以從您使用的任何網(wǎng)絡(luò)連接中檢索該數(shù)據(jù)。

網(wǎng)絡(luò)連接

在當(dāng)前狀態(tài)下,野生動(dòng)物探測器只是使用無線網(wǎng)絡(luò)連接互聯(lián)網(wǎng)。雖然這不是最實(shí)用的,特別是考慮到它很可能在沒有現(xiàn)成的無線連接的區(qū)域使用,但可以輕松修改它以支持蜂窩連接或任何其他更合適的連接。

相機(jī)

這里的相機(jī)有點(diǎn)棘手。目前 Android Things 不完全支持 USB 攝像頭,但您可以將它們視為 UART 設(shè)備。如果您不想為您的相機(jī)編寫驅(qū)動(dòng)程序,您也可以使用藍(lán)牙相機(jī),因?yàn)?Android Things 確實(shí)支持藍(lán)牙連接。如果您將 Raspberry Pi 與 Android Things 一起使用,則可以使用標(biāo)準(zhǔn)的帶狀電纜攝像頭,使用 Android 的攝像頭 API,無需太多麻煩。

更多細(xì)節(jié)

雖然這個(gè)項(xiàng)目有很多事情要做,但可以在附加的源項(xiàng)目中找到更多詳細(xì)信息。如上所述,一旦您生成了 TensorFlow 圖,您應(yīng)該能夠下載源代碼并將圖文件替換為您嘗試檢測的任何內(nèi)容。對(duì)于 Firebase 支持,您還需要?jiǎng)?chuàng)建自己的免費(fèi)Firebase 項(xiàng)目并將憑據(jù)復(fù)制到項(xiàng)目中。


下載該資料的人也在下載 下載該資料的人還在閱讀
更多 >

評(píng)論

查看更多

下載排行

本周

  1. 1山景DSP芯片AP8248A2數(shù)據(jù)手冊(cè)
  2. 1.06 MB  |  532次下載  |  免費(fèi)
  3. 2RK3399完整板原理圖(支持平板,盒子VR)
  4. 3.28 MB  |  339次下載  |  免費(fèi)
  5. 3TC358743XBG評(píng)估板參考手冊(cè)
  6. 1.36 MB  |  330次下載  |  免費(fèi)
  7. 4DFM軟件使用教程
  8. 0.84 MB  |  295次下載  |  免費(fèi)
  9. 5元宇宙深度解析—未來的未來-風(fēng)口還是泡沫
  10. 6.40 MB  |  227次下載  |  免費(fèi)
  11. 6迪文DGUS開發(fā)指南
  12. 31.67 MB  |  194次下載  |  免費(fèi)
  13. 7元宇宙底層硬件系列報(bào)告
  14. 13.42 MB  |  182次下載  |  免費(fèi)
  15. 8FP5207XR-G1中文應(yīng)用手冊(cè)
  16. 1.09 MB  |  178次下載  |  免費(fèi)

本月

  1. 1OrCAD10.5下載OrCAD10.5中文版軟件
  2. 0.00 MB  |  234315次下載  |  免費(fèi)
  3. 2555集成電路應(yīng)用800例(新編版)
  4. 0.00 MB  |  33566次下載  |  免費(fèi)
  5. 3接口電路圖大全
  6. 未知  |  30323次下載  |  免費(fèi)
  7. 4開關(guān)電源設(shè)計(jì)實(shí)例指南
  8. 未知  |  21549次下載  |  免費(fèi)
  9. 5電氣工程師手冊(cè)免費(fèi)下載(新編第二版pdf電子書)
  10. 0.00 MB  |  15349次下載  |  免費(fèi)
  11. 6數(shù)字電路基礎(chǔ)pdf(下載)
  12. 未知  |  13750次下載  |  免費(fèi)
  13. 7電子制作實(shí)例集錦 下載
  14. 未知  |  8113次下載  |  免費(fèi)
  15. 8《LED驅(qū)動(dòng)電路設(shè)計(jì)》 溫德爾著
  16. 0.00 MB  |  6656次下載  |  免費(fèi)

總榜

  1. 1matlab軟件下載入口
  2. 未知  |  935054次下載  |  免費(fèi)
  3. 2protel99se軟件下載(可英文版轉(zhuǎn)中文版)
  4. 78.1 MB  |  537798次下載  |  免費(fèi)
  5. 3MATLAB 7.1 下載 (含軟件介紹)
  6. 未知  |  420027次下載  |  免費(fèi)
  7. 4OrCAD10.5下載OrCAD10.5中文版軟件
  8. 0.00 MB  |  234315次下載  |  免費(fèi)
  9. 5Altium DXP2002下載入口
  10. 未知  |  233046次下載  |  免費(fèi)
  11. 6電路仿真軟件multisim 10.0免費(fèi)下載
  12. 340992  |  191187次下載  |  免費(fèi)
  13. 7十天學(xué)會(huì)AVR單片機(jī)與C語言視頻教程 下載
  14. 158M  |  183279次下載  |  免費(fèi)
  15. 8proe5.0野火版下載(中文版免費(fèi)下載)
  16. 未知  |  138040次下載  |  免費(fèi)