热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

我们可以在R中得到因子矩阵吗?

如何解决《我们可以在R中得到因子矩阵吗?》经验,为你挑选了2个好方法。

似乎不可能在R中得到因子矩阵.这是真的吗?如果是,为什么?如果没有,我该怎么办?

f <- factor(sample(letters[1:5], 20, rep=TRUE), letters[1:5])
m <- matrix(f,4,5)
is.factor(m) # fail.

m <- factor(m,letters[1:5])
is.factor(m) # oh, yes? 
is.matrix(m) # nope. fail. 

dim(f) <- c(4,5) # aha?
is.factor(f) # yes.. 
is.matrix(f) # yes!

# but then I get a strange behavior
cbind(f,f) # is not a factor anymore
head(f,2) # doesn't give the first 2 rows but the first 2 elements of f
# should I worry about it?

Reinstate Mo.. 20

在这种情况下,它可能像鸭子一样走路,甚至像鸭子一样嘎嘎叫,但f来自:

f <- factor(sample(letters[1:5], 20, rep=TRUE), letters[1:5])
dim(f) <- c(4,5)

真的不是一个矩阵,即使is.matrix()声称它严格是一个矩阵.就所is.matrix()涉及的矩阵而言,f只需要是一个向量并具有一个dim属性.通过添加属性给f您通过测试.然而,正如您所看到的,一旦您开始使用f矩阵,它很快就会失去使其成为一个因素的功能(您最终会使用级别或维度丢失).

实际上只有原子向量类型的矩阵和数组:

    合乎逻辑的,

    整数,

    真实,

    复杂,

    字符串(或字符),和

    生的

另外,正如@hadley提醒我的那样,你也可以有列表矩阵和数组(通过dim在列表对象上设置属性.例如,参见Hadley的书,Advanced R的Matrices&Arrays部分.)

任何超出这些类型的东西都会被强制转换为某种较低类型的东西as.vector().这发生在matrix(f, nrow = 3)不是因为f是原子根据 is.atomic()(它返回TRUEf,因为它在内部存储为一个整数和typeof(f)返回"integer"),但因为它具有class属性.这将设置OBJECT内部表示的位,f并且任何具有类的内容都应该通过以下方式强制转换为其中一种原子类型as.vector():

matrix <- function(data = NA, nrow = 1, ncol = 1, byrow = FALSE,
                   dimnames = NULL) {
    if (is.object(data) || !is.atomic(data)) 
        data <- as.vector(data)
....

通过添加维度dim<-()是一种快速创建数组而无需复制对象的方法,但这会绕过R f通过其他方法强制转换为矩阵时所做的一些检查和平衡

matrix(f, nrow = 3) # or
as.matrix(f)

当您尝试使用在矩阵上工作的基本函数或使用方法分派时,会发现这一点.请注意,在分配尺寸后f,f仍然是类"factor":

> class(f)
[1] "factor"

这解释了head()行为; 你没有得到这个head.matrix行为,因为f它不是一个矩阵,至少就S3机制而言:

> debug(head.matrix)
> head(f) # we don't enter the debugger
[1] d c a d b d
Levels: a b c d e
> undebug(head.matrix)

并且head.default方法调用[有一个factor方法,因此观察到的行为:

> debugonce(`[.factor`)
> head(f)
debugging in: `[.factor`(x, seq_len(n))
debug: {
    y <- NextMethod("[")
    attr(y, "contrasts") <- attr(x, "contrasts")
    attr(y, "levels") <- attr(x, "levels")
    class(y) <- oldClass(x)
    lev <- levels(x)
    if (drop) 
        factor(y, exclude = if (anyNA(levels(x))) 
            NULL
        else NA)
    else y
}
....

cbind()行为可以从(从记录的行为进行解释?cbind,重点煤矿):

功能cbindrbindS3通用,...

....

在默认方法中,所有向量/矩阵必须是原子(参见vector)或列表.表达是不允许的.语言对象(例如公式和调用)和pairlists将被强制转换为列表:其他对象(如名称和外部指针)将作为元素包含在列表结果中. 输入可能具有的任何类都被丢弃(特别是,因子被其内部代码替换).

同样,这其实f是阶级的"factor"是打败你,因为默认的cbind方法被调用,它将剥离水平的信息,当你观察到的返回内部整数代码.

在许多方面,你必须忽略或至少不完全信任is.foo函数告诉你的内容,因为它们只是使用简单的测试来说明某些东西是否是某个foo对象.is.matrix()is.atomic()是显然是错误的,当涉及到f(用尺寸)从一个特定点.它们在实施方面也是正确的,或者至少可以从实施中理解它们的行为; 我认为is.atomic(f)是不正确的,但如果用"如果是一个原子类型的" [R核心意思是"型"是由返回的东西typeof(f),然后is.atomic()是正确的.更严格的测试is.vector(),它f失败:

> is.vector(f)
[1] FALSE

因为它具有超出names属性的属性:

> attributes(f)
$levels
[1] "a" "b" "c" "d" "e"

$class
[1] "factor"

$dim
[1] 4 5

至于你应该如何获得因子矩阵,至少如果你想要它保留因子信息(水平的标签),你就不能.一种解决方案是使用字符矩阵,它将保留标签:

> fl <- levels(f)
> fm <- matrix(f, ncol = 5)
> fm
     [,1] [,2] [,3] [,4] [,5]
[1,] "c"  "a"  "a"  "c"  "b" 
[2,] "d"  "b"  "d"  "b"  "a" 
[3,] "e"  "e"  "e"  "c"  "e" 
[4,] "a"  "b"  "b"  "a"  "e"

并且我们存储f未来使用的级别,因为我们在此过程中会丢失一些矩阵元素.

或者使用内部整数表示:

> (fm2 <- matrix(unclass(f), ncol = 5))
     [,1] [,2] [,3] [,4] [,5]
[1,]    3    1    1    3    2
[2,]    4    2    4    2    1
[3,]    5    5    5    3    5
[4,]    1    2    2    1    5

并且您可以通过以下方式再次返回级别/标签:

> fm2[] <- fl[fm2]
> fm2
     [,1] [,2] [,3] [,4] [,5]
[1,] "c"  "a"  "a"  "c"  "b" 
[2,] "d"  "b"  "d"  "b"  "a" 
[3,] "e"  "e"  "e"  "c"  "e" 
[4,] "a"  "b"  "b"  "a"  "e"

使用数据框似乎并不理想,因为数据框的每个组件都将被视为一个单独的因素,而您似乎希望将数组视为具有一组级别的单个因子.

如果你真的想做你想要的,有一个因子矩阵,你很可能需要创建自己的S3类来完成这个,加上所有的方法.例如,您可以将因子矩阵存储为字符矩阵但"factorMatrix"存储类,其中您将级别存储在因子矩阵旁边作为额外属性.然后你需要编写[.factorMatrix,这将获取级别,然后使用[矩阵上的默认方法,然后再次添加级别属性.你也可以写cbindhead方法.然而,所需方法的列表会快速增长,但是一个简单的实现可能适合,如果你让你的对象有类c("factorMatrix", "matrix")(即继承自"matrix"类),你将获取该类的所有属性/方法"matrix"(这将删除级别和其他属性)因此您至少可以使用这些对象,并查看您需要添加新方法以填写类的行为.



1> Reinstate Mo..:

在这种情况下,它可能像鸭子一样走路,甚至像鸭子一样嘎嘎叫,但f来自:

f <- factor(sample(letters[1:5], 20, rep=TRUE), letters[1:5])
dim(f) <- c(4,5)

真的不是一个矩阵,即使is.matrix()声称它严格是一个矩阵.就所is.matrix()涉及的矩阵而言,f只需要是一个向量并具有一个dim属性.通过添加属性给f您通过测试.然而,正如您所看到的,一旦您开始使用f矩阵,它很快就会失去使其成为一个因素的功能(您最终会使用级别或维度丢失).

实际上只有原子向量类型的矩阵和数组:

    合乎逻辑的,

    整数,

    真实,

    复杂,

    字符串(或字符),和

    生的

另外,正如@hadley提醒我的那样,你也可以有列表矩阵和数组(通过dim在列表对象上设置属性.例如,参见Hadley的书,Advanced R的Matrices&Arrays部分.)

任何超出这些类型的东西都会被强制转换为某种较低类型的东西as.vector().这发生在matrix(f, nrow = 3)不是因为f是原子根据 is.atomic()(它返回TRUEf,因为它在内部存储为一个整数和typeof(f)返回"integer"),但因为它具有class属性.这将设置OBJECT内部表示的位,f并且任何具有类的内容都应该通过以下方式强制转换为其中一种原子类型as.vector():

matrix <- function(data = NA, nrow = 1, ncol = 1, byrow = FALSE,
                   dimnames = NULL) {
    if (is.object(data) || !is.atomic(data)) 
        data <- as.vector(data)
....

通过添加维度dim<-()是一种快速创建数组而无需复制对象的方法,但这会绕过R f通过其他方法强制转换为矩阵时所做的一些检查和平衡

matrix(f, nrow = 3) # or
as.matrix(f)

当您尝试使用在矩阵上工作的基本函数或使用方法分派时,会发现这一点.请注意,在分配尺寸后f,f仍然是类"factor":

> class(f)
[1] "factor"

这解释了head()行为; 你没有得到这个head.matrix行为,因为f它不是一个矩阵,至少就S3机制而言:

> debug(head.matrix)
> head(f) # we don't enter the debugger
[1] d c a d b d
Levels: a b c d e
> undebug(head.matrix)

并且head.default方法调用[有一个factor方法,因此观察到的行为:

> debugonce(`[.factor`)
> head(f)
debugging in: `[.factor`(x, seq_len(n))
debug: {
    y <- NextMethod("[")
    attr(y, "contrasts") <- attr(x, "contrasts")
    attr(y, "levels") <- attr(x, "levels")
    class(y) <- oldClass(x)
    lev <- levels(x)
    if (drop) 
        factor(y, exclude = if (anyNA(levels(x))) 
            NULL
        else NA)
    else y
}
....

cbind()行为可以从(从记录的行为进行解释?cbind,重点煤矿):

功能cbindrbindS3通用,...

....

在默认方法中,所有向量/矩阵必须是原子(参见vector)或列表.表达是不允许的.语言对象(例如公式和调用)和pairlists将被强制转换为列表:其他对象(如名称和外部指针)将作为元素包含在列表结果中. 输入可能具有的任何类都被丢弃(特别是,因子被其内部代码替换).

同样,这其实f是阶级的"factor"是打败你,因为默认的cbind方法被调用,它将剥离水平的信息,当你观察到的返回内部整数代码.

在许多方面,你必须忽略或至少不完全信任is.foo函数告诉你的内容,因为它们只是使用简单的测试来说明某些东西是否是某个foo对象.is.matrix()is.atomic()是显然是错误的,当涉及到f(用尺寸)从一个特定点.它们在实施方面也是正确的,或者至少可以从实施中理解它们的行为; 我认为is.atomic(f)是不正确的,但如果用"如果是一个原子类型的" [R核心意思是"型"是由返回的东西typeof(f),然后is.atomic()是正确的.更严格的测试is.vector(),它f失败:

> is.vector(f)
[1] FALSE

因为它具有超出names属性的属性:

> attributes(f)
$levels
[1] "a" "b" "c" "d" "e"

$class
[1] "factor"

$dim
[1] 4 5

至于你应该如何获得因子矩阵,至少如果你想要它保留因子信息(水平的标签),你就不能.一种解决方案是使用字符矩阵,它将保留标签:

> fl <- levels(f)
> fm <- matrix(f, ncol = 5)
> fm
     [,1] [,2] [,3] [,4] [,5]
[1,] "c"  "a"  "a"  "c"  "b" 
[2,] "d"  "b"  "d"  "b"  "a" 
[3,] "e"  "e"  "e"  "c"  "e" 
[4,] "a"  "b"  "b"  "a"  "e"

并且我们存储f未来使用的级别,因为我们在此过程中会丢失一些矩阵元素.

或者使用内部整数表示:

> (fm2 <- matrix(unclass(f), ncol = 5))
     [,1] [,2] [,3] [,4] [,5]
[1,]    3    1    1    3    2
[2,]    4    2    4    2    1
[3,]    5    5    5    3    5
[4,]    1    2    2    1    5

并且您可以通过以下方式再次返回级别/标签:

> fm2[] <- fl[fm2]
> fm2
     [,1] [,2] [,3] [,4] [,5]
[1,] "c"  "a"  "a"  "c"  "b" 
[2,] "d"  "b"  "d"  "b"  "a" 
[3,] "e"  "e"  "e"  "c"  "e" 
[4,] "a"  "b"  "b"  "a"  "e"

使用数据框似乎并不理想,因为数据框的每个组件都将被视为一个单独的因素,而您似乎希望将数组视为具有一组级别的单个因子.

如果你真的想做你想要的,有一个因子矩阵,你很可能需要创建自己的S3类来完成这个,加上所有的方法.例如,您可以将因子矩阵存储为字符矩阵但"factorMatrix"存储类,其中您将级别存储在因子矩阵旁边作为额外属性.然后你需要编写[.factorMatrix,这将获取级别,然后使用[矩阵上的默认方法,然后再次添加级别属性.你也可以写cbindhead方法.然而,所需方法的列表会快速增长,但是一个简单的实现可能适合,如果你让你的对象有类c("factorMatrix", "matrix")(即继承自"matrix"类),你将获取该类的所有属性/方法"matrix"(这将删除级别和其他属性)因此您至少可以使用这些对象,并查看您需要添加新方法以填写类的行为.



2> BrodieG..:

不幸的是,因子支持在R中并不完全通用,因此许多R函数默认将因子视为其内部存储类型,即integer:

> typeof(factor(letters[1:3]))
[1] "integer  

这是发生的事情matrix,cbind.他们不知道如何处理因子,但他们确实知道如何处理整数,因此他们将你的因子视为整数. head实际上恰恰相反.它确实知道如何处理一个因子,但它从来不会检查你的因子也是一个矩阵,所以只需将它视为一个普通的无量纲因子向量.

你最好的操作就好像你的矩阵有因素一样,就是强迫它去角色.完成操作后,可以将其恢复为因子形式.您也可以使用整数形式执行此操作,但是您可能会遇到奇怪的事情(例如,您可以对整数矩阵进行矩阵乘法,但这对因子没有意义).

请注意,如果您将"矩阵"类添加到您的因子中,则某些(但不是全部)事情开始起作用:

f <- factor(letters[1:9])
dim(f) <- c(3, 3)
class(f) <- c("factor", "matrix")
head(f, 2)

生产:

     [,1] [,2] [,3]
[1,] a    d    g   
[2,] b    e    h   
Levels: a b c d e f g h i

这不能解决rbind等问题.


推荐阅读
  • 一、使用Microsoft.Office.Interop.Excel.DLL需要安装Office代码如下:2publicstaticboolExportExcel(S ... [详细]
  • 本文详细介绍如何在SSM(Spring + Spring MVC + MyBatis)框架中实现分页功能。包括分页的基本概念、数据准备、前端分页栏的设计与实现、后端分页逻辑的编写以及最终的测试步骤。 ... [详细]
  • 解决JavaScript中法语字符排序问题
    在开发一个使用JavaScript、HTML和CSS的Web应用时,遇到从SQLite数据库中提取的法语词汇排序不正确的问题,特别是带重音符号的字母未按预期排序。 ... [详细]
  • This article explores the process of integrating Promises into Ext Ajax calls for a more functional programming approach, along with detailed steps on testing these asynchronous operations. ... [详细]
  • 我在尝试将组合框转换为具有自动完成功能时遇到了一个问题,即页面上的列表框也被转换成了自动完成下拉框,而不是保持原有的多选列表框形式。 ... [详细]
  • 探索CNN的可视化技术
    神经网络的可视化在理论学习与实践应用中扮演着至关重要的角色。本文深入探讨了三种有效的CNN(卷积神经网络)可视化方法,旨在帮助读者更好地理解和优化模型。 ... [详细]
  • 本文介绍如何通过Java代码调用阿里云短信服务API来实现短信验证码的发送功能,包括必要的依赖添加和关键代码示例。 ... [详细]
  • 在AngularJS中,有时需要在表单内包含某些控件,但又不希望这些控件导致表单变为脏状态。例如,当用户对表单进行修改后,表单的$dirty属性将变为true,触发保存对话框。然而,对于一些导航或辅助功能控件,我们可能并不希望它们触发这种行为。 ... [详细]
  • 2023年1月28日网络安全热点
    涵盖最新的网络安全动态,包括OpenSSH和WordPress的安全更新、VirtualBox提权漏洞、以及谷歌推出的新证书验证机制等内容。 ... [详细]
  • iOS如何实现手势
    这篇文章主要为大家展示了“iOS如何实现手势”,内容简而易懂,条理清晰,希望能够帮助大家解决疑惑,下面让小编带领大家一起研究并学习一下“iOS ... [详细]
  • 本文探讨了在 APICloud 平台使用 execScript 方法时如何正确传递对象参数,并提供了详细的示例和解释。 ... [详细]
  • 本文探讨了如何使用Scrapy框架构建高效的数据采集系统,以及如何通过异步处理技术提升数据存储的效率。同时,文章还介绍了针对不同网站采用的不同采集策略。 ... [详细]
  • 本文分享了作者在使用LaTeX过程中的几点心得,涵盖了从文档编辑、代码高亮、图形绘制到3D模型展示等多个方面的内容。适合希望深入了解LaTeX高级功能的用户。 ... [详细]
  • 视觉Transformer综述
    本文综述了视觉Transformer在计算机视觉领域的应用,从原始Transformer出发,详细介绍了其在图像分类、目标检测和图像分割等任务中的最新进展。文章不仅涵盖了基础的Transformer架构,还深入探讨了各类增强版Transformer模型的设计思路和技术细节。 ... [详细]
  • 本文详细介绍了 Redis 中的主要数据类型,包括 String、Hash、List、Set、ZSet、Geo 和 HyperLogLog,并提供了每种类型的基本操作命令和应用场景。 ... [详细]
author-avatar
FEEL欧诺_625
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有