zoukankan      html  css  js  c++  java
  • Hadoop之HDFS入门实战

    一、HDFS优缺点

    优点:

    1. 高容错性
      • 数据自动保存多个副本
      • 某一个副本丢失后,它可以自动恢复
    2. 适合处理大数据
      • 数据规模,可以达到PB级
      • 文件规模,能够处理百万规模的文件数量
    3. 可构建在廉价机器上,通过多副本保证可靠性

    缺点:

    1. 不适合低延时数据访问
    2. 不适合对大量小文件进行存储
      • 存储大量小文件,他会占用NameNode大量内存存储目录和块信息,这样不可取,因为NameNode的内存有限
      • 小文件存储的寻址时间会超过读取时间,违反HDFS设计目标
    3. 不支持并发写入、随机修改
      • 一个文件只能一个线程写入
      • 只支持追加写入,不支持随机修改

    二、HDFS组成结构

    1. NameNode
    • 管理HDFS的名称空间
    • 配置副本策略
    • 管理数据块映射信息
    • 处理客户端请求
    1. DataNode
    • 存储实际的数据库
    • 执行数据块的读/写
    1. Client
    • 文件切分,文件上传时,Client将文件切分为一个一个块
    • 与NameNode交互,获取文件位置
    • 与DataNode交互,读取或写入数据
    • 提供一些命令管理HDFS
    1. Secondary NameNode
    • 辅助NameNode
    • 紧急情况下,可以恢复NameNode

    HDFS在文件上是分块存储的,2.x版本默认块大小是128M,可以通过dfs.blocksize配置。HDFS块大小取决于磁盘传输速率

    三、HDFS的Shell操作

    1. 启动Hadoop
    sbin/start-dfs.sh
    sbin/start-yarn.sh
    
    1. -help :帮助命令

    hadoop fs -help rm

    1. -ls :显示目录信息

    hadoop fs -ls /

    1. -mkdir :创建目录
      加-p 代表创建多级目录

    hadoop fs -mkdir /study
    hadoop fs -mkdir -p /study/mmc

    1. -moveFromLocal :从本地剪切到HDFS

    hadoop fs -moveFromLocal test.txt /usr/mmc

    1. -appendToFile :追加一个文件到已存在的文件末尾

    hadoop fs -appendToFile test2.txt /usr/mmc/test.txt

    1. -cat :显示文件内容

    hadoop fs -cat /usr/mmc/test.txt

    1. -chgrp、-chmod、-chown :和linux文件系统用法一样
    2. -copyFromLocal :从本地复制到HDFS中
    3. -copyToLocal :从HDFS拷贝到本地

    hadoop fs -copyToLocal /usr/mmc/test.txt ./test.txt

    1. -cp :从HDFS的一个路径拷到另一个路径

    hadoop fs -cp /usr/mmc/test.txt /study/mmc

    1. -mv :在HDFS中移动文件
    2. -get :等同于copyToLocal

    hadoop fs -get /usr/mmc/test.txt

    1. -getmerge :合并下载多个文件

    hadoop fs -getmerge /usr/mmc/* merge.txt

    1. -put :等同于copyFromLocal
    2. -tail :显示一个文件的末尾

    hadoop fs -tail /usr/mmc/test.txt

    1. -rm :删除文件或文件夹

    hadoop fs -rm /study/mmc/test.txt

    1. -rmdif :删除空目录
    2. -du :统计文件夹大小

    hadoop fs -du -h /

    1. -setrep :设置HDFS文件的副本数

    四、HDFS的客户端操作

    1. 启动虚拟机上部署的Hadoop
    2. windows本机环境变量设置(可不设置)
    • 在系统变量中新建
    • 在系统变量的PATH中增加如下:
    1. java客户端操作HDFS
    • 引入pom文件
    
        <dependencies>
            <dependency>
                <groupId>junit</groupId>
                <artifactId>junit</artifactId>
                <version>RELEASE</version>
            </dependency>
            <dependency>
                <groupId>org.apache.logging.log4j</groupId>
                <artifactId>log4j-core</artifactId>
                <version>2.8.2</version>
            </dependency>
            <!-- https://mvnrepository.com/artifact/org.apache.hadoop/hadoop-common -->
            <dependency>
                <groupId>org.apache.hadoop</groupId>
                <artifactId>hadoop-common</artifactId>
                <version>2.10.0</version>
            </dependency>
    
            <dependency>
                <groupId>org.apache.hadoop</groupId>
                <artifactId>hadoop-client</artifactId>
                <version>2.10.0</version>
            </dependency>
    
            <dependency>
                <groupId>org.apache.hadoop</groupId>
                <artifactId>hadoop-hdfs</artifactId>
                <version>2.10.0</version>
            </dependency>
        </dependencies>
    
    • demo
    public class HDFSClient {
    
        public static void main(String[] args) throws IOException, URISyntaxException, InterruptedException {
            Configuration configuration=new Configuration();
            //获取客户端连接
            FileSystem fs=FileSystem.get(new URI("hdfs://192.168.1.21:9000"),configuration,"root");
    
            //创建目录
            fs.mkdirs(new Path("/mmc"));
    
            //关闭资源
            fs.close();
    
            System.out.println("over");
        }
    }
    
    1. API操作

    很简单,自己看api就会用

    public class HDFSClient {
    
        public static void main(String[] args) throws IOException, URISyntaxException, InterruptedException {
    
        }
    
        FileSystem fs;
    
        @Before
        public void before() throws URISyntaxException, IOException, InterruptedException {
            Configuration configuration=new Configuration();
            //获取客户端连接
            fs=FileSystem.get(new URI("hdfs://192.168.1.21:9000"),configuration,"root");
        }
    
        @Test
        public void testmkdir() throws URISyntaxException, IOException, InterruptedException {
    
            //创建目录
            fs.mkdirs(new Path("/mmc"));
    
            //关闭资源
            fs.close();
    
            System.out.println("over");
        }
    
        /**
         * 上传文件
         * @throws IOException
         */
        @Test
        public void testCopyFromLocalFile() throws IOException {
            fs.copyFromLocalFile(new Path("d://a.txt"),new Path("/mmc"));
        }
    
    
        /**
         * 删除文件
         * @throws IOException
         */
        @Test
        public void testDelete() throws IOException {
            fs.delete(new Path("/mmc"),true);
        }
    
    
        /**
         * 查看文件详情
         * @throws IOException
         */
        @Test
        public void testListFiles() throws IOException {
            RemoteIterator<LocatedFileStatus> iterator = fs.listFiles(new Path("/usr"), true);
            while (iterator.hasNext()){
                LocatedFileStatus fileStatus = iterator.next();
                if(fileStatus.isFile()){
                    System.out.println(fileStatus.getPath().getName());
                    System.out.println(fileStatus.getPermission());
                    System.out.println(fileStatus.getLen());
                }
    
            }
        }
    }
    
    1. 操作文件IO流
    
    /**
     * @description: IO流操作HDFS
     * @author: mmc
     * @create: 2020-05-28 23:01
     **/
    
    public class HDFSIO {
    
        /**
         * 上传文件
         * @throws URISyntaxException
         * @throws IOException
         * @throws InterruptedException
         */
        @Test
        public void putFileToHDFS() throws URISyntaxException, IOException, InterruptedException {
            Configuration configuration=new Configuration();
            //获取客户端连接
            FileSystem fs=FileSystem.get(new URI("hdfs://192.168.1.21:9000"),configuration,"root");
    
            //获取输入流
            FileInputStream fis=new FileInputStream("d://a.txt");
    
    
            //获取输出流
            FSDataOutputStream outputStream = fs.create(new Path("/usr/mmc/a.txt"));
    
            //复制流
            IOUtils.copyBytes(fis,outputStream,configuration);
    
            IOUtils.closeStream(fis);
            IOUtils.closeStream(outputStream);
            fs.close();
    
        }
    
    
        @Test
        public void getFileFromHDFS() throws URISyntaxException, IOException, InterruptedException{
            Configuration configuration=new Configuration();
            //获取客户端连接
            FileSystem fs=FileSystem.get(new URI("hdfs://192.168.1.21:9000"),configuration,"root");
    
            //输入流
            FSDataInputStream inputStream = fs.open(new Path("/usr/mmc/a.txt"));
    
            FileOutputStream outputStream=new FileOutputStream("e://b.txt");
    
            IOUtils.copyBytes(inputStream,outputStream,configuration);
    
            IOUtils.closeStream(outputStream);
            IOUtils.closeStream(inputStream);
            fs.close();
        }
    
        /**
         *  下载部分文件
         * @throws URISyntaxException
         * @throws IOException
         * @throws InterruptedException
         */
        public void readFileSeek1() throws URISyntaxException, IOException, InterruptedException{
            Configuration configuration=new Configuration();
            //获取客户端连接
            FileSystem fs=FileSystem.get(new URI("hdfs://192.168.1.21:9000"),configuration,"root");
    
            //输入流
            FSDataInputStream inputStream = fs.open(new Path("/usr/mmc/a.txt"));
    
            FileOutputStream outputStream=new FileOutputStream("e://b.txt.part1");
    
            //只拷贝部分流(128M)
            byte[] buf=new byte[1024];
            for (int i=0;i<1024*128;i++){
                inputStream.read(buf);
                outputStream.write(buf);
            }
    
            IOUtils.closeStream(outputStream);
            IOUtils.closeStream(inputStream);
            fs.close();
    
        }
    
        /**
         * 下载剩余部分文件
         * @throws URISyntaxException
         * @throws IOException
         * @throws InterruptedException
         */
        public void readFileSeek2() throws URISyntaxException, IOException, InterruptedException{
            Configuration configuration=new Configuration();
            //获取客户端连接
            FileSystem fs=FileSystem.get(new URI("hdfs://192.168.1.21:9000"),configuration,"root");
    
            //输入流
            FSDataInputStream inputStream = fs.open(new Path("/usr/mmc/a.txt"));
    
            //指定起点开始读取
            inputStream.seek(1024*1024*128);
    
            FileOutputStream outputStream=new FileOutputStream("e://b.txt.part2");
    
            IOUtils.copyBytes(inputStream,outputStream,configuration);
    
            IOUtils.closeStream(outputStream);
            IOUtils.closeStream(inputStream);
            fs.close();
    
        }
    }
    
    1. HDFS读写数据流程
      写数据:

      读数据:
  • 相关阅读:
    vscode 简介
    TypeScriot 深入
    TypeScript 三斜线指令
    Mysql基础(二十二):表操作:创建,删除,修改,查询表
    Mysql基础(十):函数(四)分组函数
    Mysql基础(九):函数(三)流程控制函数(IF/CASE WHEN)
    Mysql基础(七):函数(一)常见函数/单行函数分类/数学函数/日期函数/其他函数
    Mysql基础(六):sql查询(六)分页查询/联合查询
    Mysql基础(五):sql查询(五)子查询
    Mysql基础(四):sql查询(四)连接查询
  • 原文地址:https://www.cnblogs.com/javammc/p/13028140.html
Copyright © 2011-2022 走看看