94

Samsung Galaxy S3には外部 SD カード スロットがあり、 に取り付けられてい/mnt/extSdCardます。

のような方法でこのパスを取得するにはどうすればよいEnvironment.getExternalStorageDirectory()ですか?

これは を返しmnt/sdcardますが、外部 SD カードの API が見つかりません。(または、一部のタブレットではリムーバブル USB ストレージ)。

4

26 に答える 26

58

ここで見つけたソリューションのバリエーションがあります

public static HashSet<String> getExternalMounts() {
    final HashSet<String> out = new HashSet<String>();
    String reg = "(?i).*vold.*(vfat|ntfs|exfat|fat32|ext3|ext4).*rw.*";
    String s = "";
    try {
        final Process process = new ProcessBuilder().command("mount")
                .redirectErrorStream(true).start();
        process.waitFor();
        final InputStream is = process.getInputStream();
        final byte[] buffer = new byte[1024];
        while (is.read(buffer) != -1) {
            s = s + new String(buffer);
        }
        is.close();
    } catch (final Exception e) {
        e.printStackTrace();
    }

    // parse output
    final String[] lines = s.split("\n");
    for (String line : lines) {
        if (!line.toLowerCase(Locale.US).contains("asec")) {
            if (line.matches(reg)) {
                String[] parts = line.split(" ");
                for (String part : parts) {
                    if (part.startsWith("/"))
                        if (!part.toLowerCase(Locale.US).contains("vold"))
                            out.add(part);
                }
            }
        }
    }
    return out;
}

元の方法がテストされ、使用されました

  • Huawei X3(在庫)
  • Galaxy S2(在庫)
  • Galaxy S3(在庫)

これらがテストされたときに、これらがどのAndroidバージョンにあったかはわかりません。

変更したバージョンをテストしました

  • Moto Xoom 4.1.2 (株式)
  • otg ケーブルを使用した Galaxy Nexus (cyanogenmod 10)
  • HTC Incredible (cyanogenmod 7.2) これは、内部と外部の両方を返しました。このデバイスは、代わりに getExternalStorage() が sdcard へのパスを返すため、内部の大部分が使用されないという点でちょっと変わっています。

SD カードをメイン ストレージとして使用する一部の単一ストレージ デバイス

  • HTC G1 (cyanogenmod 6.1)
  • HTC G1 (株式)
  • HTC Vision/G2(在庫あり)

Incredible を除いて、これらすべてのデバイスはリムーバブル ストレージのみを返しました。おそらく、追加のチェックを行う必要がありますが、これは、これまでに見つけたどのソリューションよりも少なくとも少しは優れています。

于 2012-11-30T16:13:13.123 に答える
54

システム内のすべての SD-CARD へのパスを取得するためのより信頼できる方法を見つけました。これは、すべての Android バージョンで機能し、すべてのストレージへのパスを返します (エミュレートされたものを含む)。

すべてのデバイスで正しく動作します。

PS: Environment クラスのソース コードに基づいています。

private static final Pattern DIR_SEPORATOR = Pattern.compile("/");

/**
 * Raturns all available SD-Cards in the system (include emulated)
 *
 * Warning: Hack! Based on Android source code of version 4.3 (API 18)
 * Because there is no standart way to get it.
 * TODO: Test on future Android versions 4.4+
 *
 * @return paths to all available SD-Cards in the system (include emulated)
 */
public static String[] getStorageDirectories()
{
    // Final set of paths
    final Set<String> rv = new HashSet<String>();
    // Primary physical SD-CARD (not emulated)
    final String rawExternalStorage = System.getenv("EXTERNAL_STORAGE");
    // All Secondary SD-CARDs (all exclude primary) separated by ":"
    final String rawSecondaryStoragesStr = System.getenv("SECONDARY_STORAGE");
    // Primary emulated SD-CARD
    final String rawEmulatedStorageTarget = System.getenv("EMULATED_STORAGE_TARGET");
    if(TextUtils.isEmpty(rawEmulatedStorageTarget))
    {
        // Device has physical external storage; use plain paths.
        if(TextUtils.isEmpty(rawExternalStorage))
        {
            // EXTERNAL_STORAGE undefined; falling back to default.
            rv.add("/storage/sdcard0");
        }
        else
        {
            rv.add(rawExternalStorage);
        }
    }
    else
    {
        // Device has emulated storage; external storage paths should have
        // userId burned into them.
        final String rawUserId;
        if(Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1)
        {
            rawUserId = "";
        }
        else
        {
            final String path = Environment.getExternalStorageDirectory().getAbsolutePath();
            final String[] folders = DIR_SEPORATOR.split(path);
            final String lastFolder = folders[folders.length - 1];
            boolean isDigit = false;
            try
            {
                Integer.valueOf(lastFolder);
                isDigit = true;
            }
            catch(NumberFormatException ignored)
            {
            }
            rawUserId = isDigit ? lastFolder : "";
        }
        // /storage/emulated/0[1,2,...]
        if(TextUtils.isEmpty(rawUserId))
        {
            rv.add(rawEmulatedStorageTarget);
        }
        else
        {
            rv.add(rawEmulatedStorageTarget + File.separator + rawUserId);
        }
    }
    // Add all secondary storages
    if(!TextUtils.isEmpty(rawSecondaryStoragesStr))
    {
        // All Secondary SD-CARDs splited into array
        final String[] rawSecondaryStorages = rawSecondaryStoragesStr.split(File.pathSeparator);
        Collections.addAll(rv, rawSecondaryStorages);
    }
    return rv.toArray(new String[rv.size()]);
}
于 2013-09-18T11:29:22.540 に答える
32

私はあなたがこれを使用する必要がある外部SDカードを使用すると思います:

new File("/mnt/external_sd/")

また

new File("/mnt/extSdCard/")

あなたの場合...

の代わりにEnvironment.getExternalStorageDirectory()

私のために働きます。最初にディレクトリmntの内容を確認し、そこから作業する必要があります。


使用するSDカードを選択するには、ある種の選択方法を使用する必要があります。

File storageDir = new File("/mnt/");
if(storageDir.isDirectory()){
    String[] dirList = storageDir.list();
    //TODO some type of selecton method?
}
于 2012-07-01T09:53:37.677 に答える
16

Asus Zenfone2Marshmallow 6.0.1をチェックして解決策が機能しないまで、Dmitriy Lozenkoの解決策を使用していました。EMULATED_STORAGE_TARGET、具体的には microSD パス、つまり/storage/F99C-10F4/を取得するときにソリューションが失敗しました。コードを編集して、エミュレートされたアプリケーション パスからエミュレートされたルート パスを直接取得し、既知の電話モデル固有の物理パスを追加しました。context.getExternalFilesDirs(null);

私たちの生活を楽にするために、ここにライブラリを作りました。gradle、maven、sbt、および leiningen ビルド システム経由で使用できます。

昔ながらのやり方が好きな方は、ここからファイルを直接コピペすることもできますが、手動で確認しないと今後アップデートがあるかどうかわかりません。

ご質問やご提案がありましたら、お知らせください

于 2016-11-14T05:55:30.423 に答える
15

すべての外部ストレージ( SD カードまたは内部の取り外し不可能なストレージ) を取得するには、次のコードを使用できます。

final String state = Environment.getExternalStorageState();

if ( Environment.MEDIA_MOUNTED.equals(state) || Environment.MEDIA_MOUNTED_READ_ONLY.equals(state) ) {  // we can read the External Storage...           
    //Retrieve the primary External Storage:
    final File primaryExternalStorage = Environment.getExternalStorageDirectory();

    //Retrieve the External Storages root directory:
    final String externalStorageRootDir;
    if ( (externalStorageRootDir = primaryExternalStorage.getParent()) == null ) {  // no parent...
        Log.d(TAG, "External Storage: " + primaryExternalStorage + "\n");
    }
    else {
        final File externalStorageRoot = new File( externalStorageRootDir );
        final File[] files = externalStorageRoot.listFiles();

        for ( final File file : files ) {
            if ( file.isDirectory() && file.canRead() && (file.listFiles().length > 0) ) {  // it is a real directory (not a USB drive)...
                Log.d(TAG, "External Storage: " + file.getAbsolutePath() + "\n");
            }
        }
    }
}

または、System.getenv("EXTERNAL_STORAGE")を使用してプライマリ外部ストレージ ディレクトリ (例: "/storage/sdcard0" )を取得し、 System.getenv("SECONDARY_STORAGE")を使用してすべてのセカンダリ ディレクトリのリストを取得することもできます (例: " /storage/extSdCard:/storage/UsbDriveA:/storage/UsbDriveB" )。この場合も、USB ドライブを除外するために、セカンダリ ディレクトリのリストをフィルタリングする必要があることに注意してください。

いずれにせよ、ハードコードされたパスを使用することは常に悪いアプローチであることに注意してください (特に、すべてのメーカーが喜んで変更する可能性がある場合)。

于 2013-11-07T08:55:44.847 に答える
12

すべての外部SDカードにアクセスするために、次のことを行いました。

と:

File primaryExtSd=Environment.getExternalStorageDirectory();

次に、プライマリ外部 SD へのパスを取得します。

File parentDir=new File(primaryExtSd.getParent());

プライマリ外部ストレージの親ディレクトリを取得し、それはすべての外部 sd の親でもあります。これで、すべてのストレージを一覧表示して、必要なものを選択できます。

それが役に立つことを願っています。

于 2013-09-29T02:19:32.713 に答える
9

Android N (以前に書いたものを試すことができます) から、特に Android R から、StorageManager (ここに書いたソリューションに基づく) を使用して、より公式な新しい方法を見つけました。

class MainActivity : AppCompatActivity() {
    @RequiresApi(Build.VERSION_CODES.N)
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
        getSdCardPaths(this, true)?.forEach { volumePath ->
            Log.d("AppLog", "volumePath:$volumePath")
        }
    }

    /**
     * returns a list of all available sd cards paths, or null if not found.
     *
     * @param includePrimaryExternalStorage set to true if you wish to also include the path of the primary external storage
     */
    fun getSdCardPaths(context: Context, includePrimaryExternalStorage: Boolean): List<String>? {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            val storageManager = context.getSystemService(Context.STORAGE_SERVICE) as StorageManager
            val storageVolumes = storageManager.storageVolumes
            if (!storageVolumes.isNullOrEmpty()) {
                val primaryVolume = storageManager.primaryStorageVolume
                val result = ArrayList<String>(storageVolumes.size)
                for (storageVolume in storageVolumes) {
                    val volumePath = getVolumePath(storageVolume) ?: continue
                    if (storageVolume.uuid == primaryVolume.uuid || storageVolume.isPrimary) {
                        if (includePrimaryExternalStorage)
                            result.add(volumePath)
                        continue
                    }
                    result.add(volumePath)
                }
                return if (result.isEmpty()) null else result
            }
        }
        val externalCacheDirs = ContextCompat.getExternalCacheDirs(context)
        if (externalCacheDirs.isEmpty())
            return null
        if (externalCacheDirs.size == 1) {
            if (externalCacheDirs[0] == null)
                return null
            val storageState = EnvironmentCompat.getStorageState(externalCacheDirs[0])
            if (Environment.MEDIA_MOUNTED != storageState)
                return null
            if (!includePrimaryExternalStorage && Environment.isExternalStorageEmulated())
                return null
        }
        val result = ArrayList<String>()
        if (externalCacheDirs[0] != null && (includePrimaryExternalStorage || externalCacheDirs.size == 1))
            result.add(getRootOfInnerSdCardFolder(context, externalCacheDirs[0]))
        for (i in 1 until externalCacheDirs.size) {
            val file = externalCacheDirs[i] ?: continue
            val storageState = EnvironmentCompat.getStorageState(file)
            if (Environment.MEDIA_MOUNTED == storageState)
                result.add(getRootOfInnerSdCardFolder(context, externalCacheDirs[i]))
        }
        return if (result.isEmpty()) null else result
    }

    fun getRootOfInnerSdCardFolder(context: Context, inputFile: File): String {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
            val storageManager = context.getSystemService(Context.STORAGE_SERVICE) as StorageManager
            storageManager.getStorageVolume(inputFile)?.let {
                val result = getVolumePath(it)
                if (result != null)
                    return result
            }
        }
        var file: File = inputFile
        val totalSpace = file.totalSpace
        while (true) {
            val parentFile = file.parentFile
            if (parentFile == null || parentFile.totalSpace != totalSpace || !parentFile.canRead())
                return file.absolutePath
            file = parentFile
        }
    }

    @RequiresApi(Build.VERSION_CODES.N)
    fun getVolumePath(storageVolume: StorageVolume): String? {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R)
            return storageVolume.directory?.absolutePath
        try {
            val storageVolumeClazz = StorageVolume::class.java
            val getPath = storageVolumeClazz.getMethod("getPath")
            return getPath.invoke(storageVolume) as String
        } catch (e: Exception) {
            e.printStackTrace()
        }
        return null
    }
}
于 2014-11-28T23:38:52.570 に答える
5

皆さん、特に@SmartLemonから提供された手がかりをありがとう、私は解決策を得ました。他の誰かがそれを必要とする場合に備えて、最終的な解決策をここに置きます(最初にリストされた外部SDカードを見つけるため):

public File getExternalSDCardDirectory()
{
    File innerDir = Environment.getExternalStorageDirectory();
    File rootDir = innerDir.getParentFile();
    File firstExtSdCard = innerDir ;
    File[] files = rootDir.listFiles();
    for (File file : files) {
        if (file.compareTo(innerDir) != 0) {
            firstExtSdCard = file;
            break;
        }
    }
    //Log.i("2", firstExtSdCard.getAbsolutePath().toString());
    return firstExtSdCard;
}

外部 SD カードがない場合は、オンボード ストレージを返します。SDカードが存在しない場合はそれを使用します。変更が必要になる場合があります。

于 2013-06-25T05:38:53.647 に答える
3

私のコードを参照してください。

    Runtime runtime = Runtime.getRuntime();
    Process proc = runtime.exec("mount");
    InputStream is = proc.getInputStream();
    InputStreamReader isr = new InputStreamReader(is);
    String line;
    String mount = new String();
    BufferedReader br = new BufferedReader(isr);
    while ((line = br.readLine()) != null) {
        if (line.contains("secure")) continue;
        if (line.contains("asec")) continue;

        if (line.contains("fat")) {//TF card
            String columns[] = line.split(" ");
            if (columns != null && columns.length > 1) {
                mount = mount.concat("*" + columns[1] + "\n");
            }
        } else if (line.contains("fuse")) {//internal storage
            String columns[] = line.split(" ");
            if (columns != null && columns.length > 1) {
                mount = mount.concat(columns[1] + "\n");
            }
        }
    }
    txtView.setText(mount);
于 2013-01-17T03:03:15.903 に答える
3

System.getenv("SECONDARY_STORAGE")このソリューション(この質問に対する他の回答から組み立てられたもの)は、マシュマロでは役に立たない事実(@onoが述べたように)を処理します。

テスト済みおよび作業中:

  • Samsung Galaxy Tab 2 (Android 4.1.1 - ストック)
  • Samsung Galaxy Note 8.0 (Android 4.2.2 - ストック)
  • Samsung Galaxy S4 (Android 4.4 - ストック)
  • Samsung Galaxy S4 (Android 5.1.1 - Cyanogenmod)
  • Samsung Galaxy Tab A (Android 6.0.1 - ストック)

    /**
     * Returns all available external SD-Card roots in the system.
     *
     * @return paths to all available external SD-Card roots in the system.
     */
    public static String[] getStorageDirectories() {
        String [] storageDirectories;
        String rawSecondaryStoragesStr = System.getenv("SECONDARY_STORAGE");
    
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT) {
            List<String> results = new ArrayList<String>();
            File[] externalDirs = applicationContext.getExternalFilesDirs(null);
            for (File file : externalDirs) {
                String path = file.getPath().split("/Android")[0];
                if((Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && Environment.isExternalStorageRemovable(file))
                        || rawSecondaryStoragesStr != null && rawSecondaryStoragesStr.contains(path)){
                    results.add(path);
                }
            }
            storageDirectories = results.toArray(new String[0]);
        }else{
            final Set<String> rv = new HashSet<String>();
    
            if (!TextUtils.isEmpty(rawSecondaryStoragesStr)) {
                final String[] rawSecondaryStorages = rawSecondaryStoragesStr.split(File.pathSeparator);
                Collections.addAll(rv, rawSecondaryStorages);
            }
            storageDirectories = rv.toArray(new String[rv.size()]);
        }
        return storageDirectories;
    }
    
于 2016-09-07T14:01:39.603 に答える
2

実際、一部のデバイスでは、外部 SD カードのデフォルト名が として表示されextSdCard、他のデバイスではsdcard1.

このコード スニペットは、その正確なパスを見つけるのに役立ち、外部デバイスのパスを取得するのに役立ちます。

String sdpath,sd1path,usbdiskpath,sd0path;    
        if(new File("/storage/extSdCard/").exists())
            {
               sdpath="/storage/extSdCard/";
               Log.i("Sd Cardext Path",sdpath);
            }
        if(new File("/storage/sdcard1/").exists())
         {
              sd1path="/storage/sdcard1/";
              Log.i("Sd Card1 Path",sd1path);
         }
        if(new File("/storage/usbcard1/").exists())
         {
              usbdiskpath="/storage/usbcard1/";
              Log.i("USB Path",usbdiskpath);
         }
        if(new File("/storage/sdcard0/").exists())
         {
              sd0path="/storage/sdcard0/";
              Log.i("Sd Card0 Path",sd0path);
         }
于 2014-05-19T11:59:52.170 に答える
2

はい。異なるメーカーは、Samsung Tab 3 の extsd のように異なる SDcard 名を使用し、他の samsung デバイスは、この異なるメーカーが異なる名前を使用するように sdcard を使用します。

私はあなたと同じ要件を持っていました。だから私は私のプロジェクトからあなたのためのサンプル例を作成しましたこのリンクに移動し、androi-dirchooser ライブラリを使用するAndroid ディレクトリ チューザーの例を参照してください。この例では、SD カードを検出し、すべてのサブフォルダーを一覧表示します。また、デバイスに複数の SD カードがあるかどうかも検出します。

コードの一部は次のようになります。完全な例については、リンクAndroid Directory Chooserにアクセスしてください。

/**
* Returns the path to internal storage ex:- /storage/emulated/0
 *
* @return
 */
private String getInternalDirectoryPath() {
return Environment.getExternalStorageDirectory().getAbsolutePath();
 }

/**
 * Returns the SDcard storage path for samsung ex:- /storage/extSdCard
 *
 * @return
 */
    private String getSDcardDirectoryPath() {
    return System.getenv("SECONDARY_STORAGE");
}


 mSdcardLayout.setOnClickListener(new OnClickListener() {
    @Override
    public void onClick(View view) {
        String sdCardPath;
        /***
         * Null check because user may click on already selected buton before selecting the folder
         * And mSelectedDir may contain some wrong path like when user confirm dialog and swith back again
         */

        if (mSelectedDir != null && !mSelectedDir.getAbsolutePath().contains(System.getenv("SECONDARY_STORAGE"))) {
            mCurrentInternalPath = mSelectedDir.getAbsolutePath();
        } else {
            mCurrentInternalPath = getInternalDirectoryPath();
        }
        if (mCurrentSDcardPath != null) {
            sdCardPath = mCurrentSDcardPath;
        } else {
            sdCardPath = getSDcardDirectoryPath();
        }
        //When there is only one SDcard
        if (sdCardPath != null) {
            if (!sdCardPath.contains(":")) {
                updateButtonColor(STORAGE_EXTERNAL);
                File dir = new File(sdCardPath);
                changeDirectory(dir);
            } else if (sdCardPath.contains(":")) {
                //Multiple Sdcards show root folder and remove the Internal storage from that.
                updateButtonColor(STORAGE_EXTERNAL);
                File dir = new File("/storage");
                changeDirectory(dir);
            }
        } else {
            //In some unknown scenario at least we can list the root folder
            updateButtonColor(STORAGE_EXTERNAL);
            File dir = new File("/storage");
            changeDirectory(dir);
        }


    }
});
于 2014-09-06T07:27:57.293 に答える
1

System.getenv("SECONDARY_STORAGE")Marshmallow の場合は null を返します。これは、すべての外部ディレクトリを見つける別の方法です。内部/外部かどうかを決定する取り外し可能かどうかを確認できます

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
    File[] externalCacheDirs = context.getExternalCacheDirs();
    for (File file : externalCacheDirs) {
        if (Environment.isExternalStorageRemovable(file)) {
            // It's a removable storage
        }
    }
}
于 2016-07-05T22:52:54.143 に答える
1

一部のデバイス (たとえば、samsung galaxy sII) では、内部メモリ カードが vfat になっている場合があります。この場合、参照最後のコードを使用すると、内部メモリ カード (/mnt/sdcad) のパスが取得されますが、外部カードは取得されません。以下のコードを参照して、この問題を解決してください。

static String getExternalStorage(){
         String exts =  Environment.getExternalStorageDirectory().getPath();
         try {
            FileReader fr = new FileReader(new File("/proc/mounts"));       
            BufferedReader br = new BufferedReader(fr);
            String sdCard=null;
            String line;
            while((line = br.readLine())!=null){
                if(line.contains("secure") || line.contains("asec")) continue;
            if(line.contains("fat")){
                String[] pars = line.split("\\s");
                if(pars.length<2) continue;
                if(pars[1].equals(exts)) continue;
                sdCard =pars[1]; 
                break;
            }
        }
        fr.close();
        br.close();
        return sdCard;  

     } catch (Exception e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
    return null;
}
于 2013-11-27T07:32:10.317 に答える
0
String secStore = System.getenv("SECONDARY_STORAGE");

File externalsdpath = new File(secStore);

これにより、外部 sd セカンダリ ストレージのパスが取得されます。

于 2016-10-10T13:41:34.420 に答える
0

HTC One X (Android) でSD カードのファイルにアクセスするには、次のパスを使用します。

file:///storage/sdcard0/folder/filename.jpg

トリプル "/" に注意してください!

于 2014-11-27T01:51:57.430 に答える
0

Context.getExternalCacheDirs() または Context.getExternalFilesDirs() または Context.getObbDirs() のようなものを使用できます。それらは、アプリケーションがそのファイルを保存できるすべての外部ストレージ デバイスに、アプリケーション固有のディレクトリを提供します。

このようなもの - Context.getExternalCacheDirs()[i].getParentFile().getParentFile().getParentFile().getParent() は、外部ストレージ デバイスのルート パスを取得できます。

これらのコマンドは別の目的のためであることは知っていますが、他の答えはうまくいきませんでした。

このリンクは私に良い指針を与えてくれました - https://possiblemobile.com/2014/03/android-external-storage/

于 2016-06-28T06:38:13.870 に答える
0

Samsung Galaxy Tab S2 (モデル: T819Y)でDmitriy LozenkoGnathonicが提供するソリューションを試しましたが、外部 SD カード ディレクトリへのパスを取得するのに役立つものはありませんでした。コマンドの実行には、外部 SD カード ディレクトリ(つまり、/Storage/A5F9-15F4)への必要なパスが含まれていましたが、正規表現と一致しなかったため、返されませんでした。サムスンが従うディレクトリ命名メカニズムがわかりません。なぜ彼らは標準から逸脱し(つまりextsdcard) 、私の場合(つまり/Storage/A5F9-15F4)のように本当に怪しいものを思いつきます。不足しているものはありますか?とにかく、 Gnathonic の正規表現の次の変更mount解決策は、有効なsdcardディレクトリを取得するのに役立ちました:

final HashSet<String> out = new HashSet<String>();
        String reg = "(?i).*(vold|media_rw).*(sdcard|vfat|ntfs|exfat|fat32|ext3|ext4).*rw.*";
        String s = "";
        try {
            final Process process = new ProcessBuilder().command("mount")
                    .redirectErrorStream(true).start();
            process.waitFor();
            final InputStream is = process.getInputStream();
            final byte[] buffer = new byte[1024];
            while (is.read(buffer) != -1) {
                s = s + new String(buffer);
            }
            is.close();
        } catch (final Exception e) {
            e.printStackTrace();
        }

        // parse output
        final String[] lines = s.split("\n");
        for (String line : lines) {
            if (!line.toLowerCase(Locale.US).contains("asec")) {
                if (line.matches(reg)) {
                    String[] parts = line.split(" ");
                    for (String part : parts) {
                        if (part.startsWith("/"))
                            if (!part.toLowerCase(Locale.US).contains("vold"))
                                out.add(part);
                    }
                }
            }
        }
        return out;

これが有効な解決策であるかどうか、また他の Samsung タブレットで結果が得られるかどうかはわかりませんが、今のところ問題は解決しています。以下は、Android (v6.0) でリムーバブル SD カードのパスを取得する別の方法です。私はアンドロイドマシュマロでメソッドをテストしましたが、うまくいきます。ここで使用されるアプローチは非常に基本的なものであり、他のバージョンでも確実に機能しますが、テストは必須です。それについてのいくつかの洞察が役に立ちます:

public static String getSDCardDirPathForAndroidMarshmallow() {

    File rootDir = null;

    try {
        // Getting external storage directory file
        File innerDir = Environment.getExternalStorageDirectory();

        // Temporarily saving retrieved external storage directory as root
        // directory
        rootDir = innerDir;

        // Splitting path for external storage directory to get its root
        // directory

        String externalStorageDirPath = innerDir.getAbsolutePath();

        if (externalStorageDirPath != null
                && externalStorageDirPath.length() > 1
                && externalStorageDirPath.startsWith("/")) {

            externalStorageDirPath = externalStorageDirPath.substring(1,
                    externalStorageDirPath.length());
        }

        if (externalStorageDirPath != null
                && externalStorageDirPath.endsWith("/")) {

            externalStorageDirPath = externalStorageDirPath.substring(0,
                    externalStorageDirPath.length() - 1);
        }

        String[] pathElements = externalStorageDirPath.split("/");

        for (int i = 0; i < pathElements.length - 1; i++) {

            rootDir = rootDir.getParentFile();
        }

        File[] files = rootDir.listFiles();

        for (File file : files) {
            if (file.exists() && file.compareTo(innerDir) != 0) {

                // Try-catch is implemented to prevent from any IO exception
                try {

                    if (Environment.isExternalStorageRemovable(file)) {
                        return file.getAbsolutePath();

                    }
                } catch (Exception e) {
                    e.printStackTrace();
                }

            }
        }
    } catch (Exception ex) {
        ex.printStackTrace();
    }
    return null;
}

この問題を処理するための他のアプローチがある場合は、親切に共有してください。ありがとう

于 2016-10-19T05:43:08.637 に答える
0

このコードがあなたの問題を確実に解決すると確信しています...これは私にとってはうまく機能しています...\

try {
            File mountFile = new File("/proc/mounts");
            usbFoundCount=0;
            sdcardFoundCount=0;
            if(mountFile.exists())
             {
                Scanner usbscanner = new Scanner(mountFile);
                while (usbscanner.hasNext()) {
                    String line = usbscanner.nextLine();
                    if (line.startsWith("/dev/fuse /storage/usbcard1")) {
                        usbFoundCount=1;
                        Log.i("-----USB--------","USB Connected and properly mounted---/dev/fuse /storage/usbcard1" );
                    }
            }
         }
            if(mountFile.exists()){
                Scanner sdcardscanner = new Scanner(mountFile);
                while (sdcardscanner.hasNext()) {
                    String line = sdcardscanner.nextLine();
                    if (line.startsWith("/dev/fuse /storage/sdcard1")) {
                        sdcardFoundCount=1;
                        Log.i("-----USB--------","USB Connected and properly mounted---/dev/fuse /storage/sdcard1" );
                    }
            }
         }
            if(usbFoundCount==1)
            {
                Toast.makeText(context,"USB Connected and properly mounted", 7000).show();
                Log.i("-----USB--------","USB Connected and properly mounted" );
            }
            else
            {
                Toast.makeText(context,"USB not found!!!!", 7000).show();
                Log.i("-----USB--------","USB not found!!!!" );

            }
            if(sdcardFoundCount==1)
            {
                Toast.makeText(context,"SDCard Connected and properly mounted", 7000).show();
                Log.i("-----SDCard--------","SDCard Connected and properly mounted" );
            }
            else
            {
                Toast.makeText(context,"SDCard not found!!!!", 7000).show();
                Log.i("-----SDCard--------","SDCard not found!!!!" );

            }
        }catch (Exception e) {
            e.printStackTrace();
        } 
于 2014-06-09T07:07:33.277 に答える
0
//manifest file outside the application tag
//please give permission write this 
//<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
        File file = new File("/mnt");
        String[] fileNameList = file.list(); //file names list inside the mnr folder
        String all_names = ""; //for the log information
        String foundedFullNameOfExtCard = ""; // full name of ext card will come here
        boolean isExtCardFounded = false;
        for (String name : fileNameList) {
            if (!isExtCardFounded) {
                isExtCardFounded = name.contains("ext");
                foundedFullNameOfExtCard = name;
            }
            all_names += name + "\n"; // for log
        }
        Log.d("dialog", all_names + foundedFullNameOfExtCard);
于 2017-04-13T21:17:26.677 に答える
-1

それは真実ではない。/mnt/sdcard/external_sd は、SD カードがマウントされていなくても存在できます。マウントされていないときに /mnt/sdcard/external_sd に書き込もうとすると、アプリケーションがクラッシュします。

次を使用して、SDカードが最初にマウントされているかどうかを確認する必要があります。

boolean isSDPresent = Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED);
于 2012-11-15T10:41:24.370 に答える
-1

次の手順は私にとってはうまくいきました。次の行を書くだけです。

String sdf = new String(Environment.getExternalStorageDirectory().getName());
String sddir = new String(Environment.getExternalStorageDirectory().getPath().replace(sdf,""));

最初の行は sd ディレクトリの名前を示し、2 番目の文字列の replace メソッドでそれを使用するだけです。2 番目の文字列には、内部およびリムーバブルsd(/storage/ 私の場合)のパスが含まれます。アプリにこのパスが必要でしたが、必要に応じてさらに先に進むことができます。

于 2016-03-01T05:23:17.487 に答える
-1

Galaxy S3 Android 4.3 では、私が使用するパスは./storage/extSdCard/Card/であり、それが機能します。それが役に立てば幸い、

于 2013-12-20T15:46:14.313 に答える