使用一些约束将R中的矩阵/数据帧转换为JSON对象

时间:2014-07-19 12:03:16

标签: json r matrix rjson rjsonio

REDITED:

我必须将R中的矩阵转换为JSON对象,其中包含一些结构。我正在使用rjson包。通过一个例子,让我说明我想要的。我的具体情况是R中推荐系统代码的输出,其中X2 X3是与特定项目X1最接近的两个项目。此外,X4,X5是与该行的(X1,X2)和(X1,X3)相关的相似度得分。我希望每个项目的所有推荐项目都是JSON对象和每个项目以及推荐的JSON对象项目作为更大的JSON对象。分数也应该合并到JSON结构中。

让我通过一个例子来解释。

假设我有一个矩阵

X1 X2 X3 X4 X5 
1 22 23  0.8 0.5
34 4 87  0.4 0.4
23 7 92  0.6 0.5

我希望每个项目的JSON结构(每行每个X1)以及每个组合的推荐项目和相似度得分作为单独的JSON实体,这是按顺序完成的。我不想要一个包含这些单独的JSON对象的整个JSON对象。 假设还有一个名为“coid”的实体将作为代码的输入。我假设它是XYZ,并且对于所有行都是相同的。

{ "_id" : { "coid" : "XYZ", "iid" : "1"}, "items" : [ { "item" : "22", "score" : 0.8},{ "item": "23", "score" : 0.5}] }
{ "_id" : { "coid" : "XYZ", "iid" : "34"},"items" : [ { "item" : "4", "score" : 0.4},{ "item": "87", "score" : 0.4}] }
{ "_id" : { "coid" : "XYZ", "iid" : "23"},"items" : [ { "item" : "7", "score" : 0.6},{ "item": "92", "score" : 0.5}] }

如上所述,每个实体都是一个有效的JSON结构/对象,但它们不会整体放在一个单独的JSON对象中。

我感谢上一个问题所做的所有帮助,但不知怎的,我觉得我在这里的这个新改动与它们无关,因为最后,如果你做一个toJSON(某个实体),那么它将整个事物转换为一个JSON对象。我不希望这样。 我希望像这样的个人写入文件。

对于我的无知和不便,我感到非常抱歉。请帮忙。 感谢。

3 个答案:

答案 0 :(得分:2)

首先,你的json无效。您可以检查有效性,例如here

话虽这么说,为了获得类似于你想要的json输出的东西,你可以做f

library(RJSONIO)

# recreating your matrix
m <- matrix(c(1,22,23,34,4,87,23,7,92),nrow=3,byrow=T)
colnames(m)<-c('X1','X2','X3')

# convert numeric matrix to character (if necessary)
m <- matrix(as.character(m),nrow=nrow(m))

# transform your matrix before turning into json    
p <- apply(m,MARGIN=1,FUN=function(r)list(Item=unname(r[1]),Recos=unname(r[-1])))

# jsonize
toJSON(p)

结果:

[
    {
        "Item" : "1",
        "Recos" : ["22", "23"]
    },
    {
        "Item" : "34",
        "Recos" : ["4", "87"]
    },
    {
        "Item" : "23",
        "Recos" : ["7", "92"]
    }
]

编辑(根据您的修改):

library(RJSONIO)

# recreating your matrix
m <- matrix(c(1,22,23,34,4,87,23,7,92),nrow=3,byrow=T)
colnames(m)<-c('X1','X2','X3')

# transform your matrix before turning into json    
p <- apply(m,MARGIN=1,
           FUN=function(r){
             list(itemID=unname(r[1]),
                  recommendedItems=lapply(unname(r[-1]),
                                          FUN=function(i)list(itemID=i)))
           })

# jsonize
toJSON(p)

结果:

[{
        "itemID" : 1,
        "recommendedItems" : [{
                "itemID" : 22
            }, {
                "itemID" : 23
            }
        ]
    }, {
        "itemID" : 34,
        "recommendedItems" : [{
                "itemID" : 4
            }, {
                "itemID" : 87
            }
        ]
    }, {
        "itemID" : 23,
        "recommendedItems" : [{
                "itemID" : 7
            }, {
                "itemID" : 92
            }
        ]
    }
]

编辑2:

我宁愿尝试解释如何通过RJSONIO包将R结构转换为json,而不是为您编写代码。

就json转换而言,我考虑3种“类型”的对象:

  1. 未命名的列表(或矢量)
  2. 命名列表(或矢量)
  3. 一个元素的向量
  4. 1)元素的未命名列表(或向量)(例如v <- list('a','b','c'))将转换为json:

    [ element_1, element_2, element_3, ... ]
    

    element_n是列表的第n个元素。当然,列表中的每个元素都可以是另一个复杂的对象,按照我在这里描述的3条规则转换为json。

    2)命名列表(或矢量)(例如n <- list(A="foo",B="bar"))将被翻译为json:

    { "name_1": value_1, "name_2": value_2, ...  }
    

    name_n是命名列表的第n个元素的名称,value_1是命名列表的第n个元素的值。当然,命名列表的每个值又可以是另一个复杂的对象,它按照我在这里描述的3条规则转换为json。

    3)正如您可以正确指出的那样,R中的每个对象都是一个向量。偶数a <- 1是一个元素的数字向量。因此,按照前面的两条规则,您可能希望将list(x=1)翻译为{ "x" : [ 1 ] }。但是由于asIs函数的参数toJSON(默认为FALSE),单个元素的向量(不是列表)被视为标量。

    话虽如此,下面是一些例子:

    toJSON(list(list(A=2),1:3))
    > '[ { "A": 2 }, [ 1, 2, 3 ] ]'
    
    toJSON(list(A=list(1),B=list(C="X"),D=1))
    > '{ "A": [ 1 ], "B": { "C": "X" }, "D": 1 }'
    

答案 1 :(得分:0)

所需的json对象无效。您应该将data.frame转换为列表,然后再将其转换为json对象。例如,您可以这样做:

cat(toJSON(apply(dat,1,function(x)list(item =unname(x[1]),
                                       Recos=unname(x[-1])))))

[
 {
 "item": 1,
"Recos": [ 22, 23 ] 
},
{
 "item": 34,
"Recos": [ 4, 87 ] 
},
{
 "item": 23,
"Recos": [ 7, 92 ] 
} 
]

答案 2 :(得分:0)

您需要创建适当的嵌套列表

m <- matrix(c(1,22,23,34,4,87,23,7,92),nrow=3,byrow=T)
colnames(m)<-c('X1','X2','X3')

m1 <- apply(m,1, function(x) {
     list(itemID = unname(x[1]), 
          recommendedItems = lapply(unname(x[2:3]), function(y) {
             list(itemID = y)}
          ))
       })


 cat(toJSON(m1))
[
  {
    "itemID":      1,
    "recommendedItems": [
      {
        "itemID":     22 
      },
      {
        "itemID":     23 
      } 
    ] 
  },
{
    "itemID":     34,
    "recommendedItems": [
      {
        "itemID":      4 
      },
      {
        "itemID":     87 
      } 
    ] 
  },
{
    "itemID":     23,
    "recommendedItems": [
      {
        "itemID":      7 
      },
      {
        "itemID":     92 
      } 
    ] 
  } 
]