zoukankan      html  css  js  c++  java
  • R语言 data.frame 大全

    A data frame is used for storing data tables. It is a list of vectors of equal length. For example, the following variable df is a data frame containing three vectors n, s, b.

    > n = c(2, 3, 5) 
    > s = c("aa", "bb", "cc") 
    > b = c(TRUE, FALSE, TRUE) 
    > df = data.frame(n, s, b)       # df is a data frame

     

    Build-in Data Frame

    We use built-in data frames in R for our tutorials. For example, here is a built-in data frame in R, called mtcars.

    > mtcars 
                   mpg cyl disp  hp drat   wt ... 
    Mazda RX4     21.0   6  160 110 3.90 2.62 ... 
    Mazda RX4 Wag 21.0   6  160 110 3.90 2.88 ... 
    Datsun 710    22.8   4  108  93 3.85 2.32 ... 
                   ............

    The top line of the table, called the header, contains the column names. Each horizontal line afterward denotes a data row, which begins with the name of the row, and then followed by the actual data. Each data member of a row is called a cell.

    To retrieve data in a cell, we would enter its row and column coordinates in the single square bracket "[]" operator. The two coordinates are separated by a comma. In other words, the coordinates begins with row position, then followed by a comma, and ends with the column position. The order is important.

    Here is the cell value from the first row, second column of mtcars.

    > mtcars[1, 2] 
    [1] 6

    Moreover, we can use the row and column names instead of the numeric coordinates.

    mtcars["Mazda RX4", "cyl"] 
    [1] 6

    Lastly, the number of data rows in the data frame is given by the nrow function.

    nrow(mtcars)    # number of data rows 
    [1] 32

    And the number of columns of a data frame is given by the ncol function.

    > ncol(mtcars)    # number of columns 
    [1] 11

    Further details of the mtcars data set is available in the R documentation.

    help(mtcars)

     

    Preview

    Instead of printing out the entire data frame, it is often desirable to preview it with the head function beforehand.

    > head(mtcars) 
                   mpg cyl disp  hp drat   wt ... 
    Mazda RX4     21.0   6  160 110 3.90 2.62 ... 
                   ............
     
     ##################################################

    访问元素

    与Matrix一样,使用[行Index,列Index]的格式可以访问具体的元素。
    比如访问第一行:
    student[1,]
    访问第二列:
    student[,2]
    使用列的Index或者列名可以选取要访问的哪些列。比如要ID和Name,那么代码为:
    idname<-student[1:2]
    或者是
    idname<-student[c("ID","Name”)]
    如果是只访问某一列,返回的是Vector类型的,那么可以使用[[或者$来访问。比如我们要所有student的Name,代码为:
    name<-student[[2]] 或者name<-student[[“Name”]] 或者name<-student$Name
    使用attach和detach函数可以使得访问列时不需要总是跟着变量名在前面。
    比如要打印所有Name,那么可以写成:
    attach(student)
    print(Name)
    detach(student)
    还可以换一种简洁一点的写法就是用with函数:
    with(student,{
      n<-Name
      print(n)
    })
    这里的n作用域只在大括号内,如果想在with函数中对全局的变量进行赋值,那么需要使用<<-这样一个运算符。

    修改列数据类型

    接下来我们查看该对象每列的类型,使用str(student)可以得到如下结果:
    'data.frame':3 obs. of  4 variables:
     $ ID       : num  1 2 3
     $ Name     : Factor w/ 3 levels "Devin","Edward",..: 1 2 3
     $ Gender   : Factor w/ 2 levels "F","M": 2 2 1
     $ Birthdate: Factor w/ 3 levels "1983-5-6","1984-12-29",..: 2 1 3
    默认情况下,字符串向量都会被自动识别成Factor,也就是说,ID是数字类型,其他的3个列都被定义为Factor类型了。显然这里Name应该是字符串类型,Birthdate应该是Date类型,我们需要对列的数据类型进行更改:
    student$Name<-as.character(student$Name)
    student$Birthdate<-as.Date(student$Birthdate)
    下面我们再运行str(student)看看修改后的结果:
    'data.frame':3 obs. of  4 variables:
     $ ID       : num  11 12 13
     $ Name     : chr  "Devin" "Edward" "Wenli"
     $ Gender   : Factor w/ 2 levels "F","M": 2 2 1
     $ Birthdate: Date, format: "1984-12-29" "1983-05-06" "1986-08-08”

    添加新列

    对于以及存在的student对象,我们希望增加Age列,该列是根据Birthdate算出来的。首先需要知道怎么算年龄。我们可以使用日期函数Sys.Date()获得当前的日期,然后使用format函数获得年份,然后用两个年份相减就是年龄。好像R并没有提供几个能用的日期函数,我们只能使用format函数取出年份部分,然后转换为int类型相减。
    student$Age<-as.integer(format(Sys.Date(),"%Y"))-as.integer(format(student$Birthdate,"%Y”))
    这样写似乎太长了,我们可以用within函数,这个函数和之前提到过的with函数类似,可以省略变量名,不同的地方是within函数可以在其中修改变量,也就是我们这里增加Age列:
    student<-within(student,{
      Age<-as.integer(format(Sys.Date(),"%Y"))-as.integer(format(Birthdate,"%Y"))
    })

    查询/子集

    查询一个Date Frame,返回一个满足条件的子集,这相当于数据库中的表查询,是非常常见的操作。使用行和列的Index来获取子集是最简单的方法,前面已经提到过。如果我们使用布尔向量,配合which函数,可以实现对行的过滤。比如我们要查询所有Gender为F的数据,那么我们首先对student$Gender==“F”,得到一个布尔向量:FALSE FALSE  TRUE,然后使用which函数可以将布尔向量中TRUE的Index返回,所以我们的完整查询语句就是:
    student[which(student$Gender=="F"),]
    注意这里列Index并没有输入,如果我们只想知道所有女生的年龄,那么可以改为:
    student[which(student$Gender=="F"),"Age”]
    这样的查询写法还是复杂了点,可以直接使用subset函数,那么查询会简单些,比如我们把查询条件改为年龄<30的女性,查姓名和年龄,那么查询语句为:
    subset(student,Gender=="F" & Age<30 ,select=c("Name","Age"))
     
    示例:
    x.sub <- subset(x.df, y > 2)
    x.sub1 <- subset(x.df, y > 2 & V1 > 0.6)
    newdata <- subset(mydata, age >= 20 | age < 10, select=c(ID, Weight))
    newdata <- subset(mydata, sex=="m" & age > 25, select=weight:income)
    x.sub2 <- subset(x.df, y > 2 & V2 > 0.4, select = c(V1, V4))
    x.sub3 <- subset(x.df, y > 3, select = V2:V5)
    x.sub4 <- x.df[x.df$y == 1, ]
    x.sub5 <- x.df[x.df$y %in% c(1, 4), ]
     
    使用SQL查询Data Frame
    对于我这种使用了多年SQL的人来说,如果能够直接写SQL语句对Data Frame进行查询操作,那是多么方便美妙的啊,结果还真有这么一个包:sqldf。
    同样是前面的需求,对应的语句就是:
    library(sqldf)
    result<-sqldf("select Name,Age from student where Gender='F' and Age<30")

    连接/合并

    对于数据库来说,对多表进行join查询是一个很正常的事情,那么在R中也可以对多个Data Frame进行连接,这就需要使用merge函数。
    比如除了前面申明的student对象外,我们再申明一个score变量,记录了每个学生的科目和成绩:
    score<-data.frame(SID=c(11,11,12,12,13),Course=c("Math","English","Math","Chinese","Math"),Score=c(90,80,80,95,96))
    我们看看该表的内容:
      SID  Course Score
    1  11    Math    90
    2  11 English    80
    3  12    Math    80
    4  12 Chinese    95
    5  13    Math    96
    这里的SID就是Student里面的ID,相当于一个外键,现在要用这个ID进行inner join操作,那么对应的R语句就是:
    result<-merge(student,score,by.x="ID",by.y="SID")
    我们看看merge以后的结果:
     ID   Name Gender  Birthdate Age  Course Score
    1 11  Devin      M 1984-12-29  31    Math    90
    2 11  Devin      M 1984-12-29  31 English    80
    3 12 Edward      M 1983-05-06  32    Math    80
    4 12 Edward      M 1983-05-06  32 Chinese    95
    5 13  Wenli      F 1986-08-08  29    Math    96
    正如我们期望的一样join在了一起。
    除了join,另外一个操作就是union,这也是数据库常用操作,那么在R中如何将两个列一样的Data Frame Union联接在一起呢?虽然R语言中有union函数,但是不是SQL的Union的意思,我们要实现Union功能,需要用到rbind函数。
    rbind的两个Data Frame必须有相同的列,比如我们再申明一个student2,将两个变量rbind起来:
    student2<-data.frame(ID=c(21,22),Name=c("Yan","Peng"),Gender=c("F","M"),Birthdate=c("1982-2-9","1983-1-16"),Age=c(32,31))
    rbind(student,student2)
  • 相关阅读:
    1046 Shortest Distance (20 分)(模拟)
    1004. Counting Leaves (30)PAT甲级真题(bfs,dfs,树的遍历,层序遍历)
    1041 Be Unique (20 分)(hash散列)
    1036 Boys vs Girls (25 分)(查找元素)
    1035 Password (20 分)(字符串处理)
    1044 Shopping in Mars (25 分)(二分查找)
    onenote使用小Tip总结^_^(不断更新中...)
    1048 Find Coins (25 分)(hash)
    三个故事
    领导者的举止
  • 原文地址:https://www.cnblogs.com/emanlee/p/6858765.html
Copyright © 2011-2022 走看看