Main File for part II of basal attributes article

Author

Julius Fenn

Notes

prepare data

set up data.frame questionnaires

setwd("outputs")
# > pre study
suppressMessages(read_file('preCAM.txt') %>%
                   # ... split it into lines ...
                   str_split('\n') %>% first() %>%
                   # ... filter empty rows ...
                   discard(function(x) x == '') %>%
                   discard(function(x) x == '\r') %>%
                   # ... parse JSON into a data.frame
                   map_dfr(fromJSON, flatten=TRUE)) -> dat_preCAM
# > post first CAM
read_file('postCAM.txt') %>%
                   # ... split it into lines ...
                   str_split('\n') %>% first() %>%
                   # ... filter empty rows ...
                   discard(function(x) x == '') %>%
                   discard(function(x) x == '\r') -> tmp_postCAM


tmp_out <- list()
for(i in 1:length(tmp_postCAM)){
tmp_out[[i]] <- fromJSON(tmp_postCAM[i])
tmp_out[[i]]$"21" <- NULL # causes error
}


dat_postCAM = dplyr::bind_rows(tmp_out)







########################################
# create counter variable for both data sets
########################################
### pre study
dat_preCAM$ID <- NA

tmp_IDcounter <- 0
for(i in 1:nrow(dat_preCAM)){
  if(!is.na(dat_preCAM$sender[i]) && dat_preCAM$sender[i] == "Greetings"){
    # tmp <- dat_preCAM$prolific_pid[i]
    tmp_IDcounter = tmp_IDcounter + 1
  }
  dat_preCAM$ID[i] <- tmp_IDcounter
}



### post study
dat_postCAM$ID <- NA

tmp_IDcounter <- 0
for(i in 1:nrow(dat_postCAM)){
  if(!is.na(dat_postCAM$sender[i]) && dat_postCAM$sender[i] == "CAMfeedbackGeneral"){
    # tmp <- dat_postCAM$prolific_pid[i]
    tmp_IDcounter = tmp_IDcounter + 1
  }
  dat_postCAM$ID[i] <- tmp_IDcounter
}



########################################
# keep only complete data sets
########################################
### pre-study
# sort(table(dat_preCAM$ID))
sum(table(dat_preCAM$ID) != max(table(dat_preCAM$ID)))
[1] 0
sum(table(dat_preCAM$ID) == max(table(dat_preCAM$ID)))
[1] 193
dat_preCAM <- dat_preCAM[dat_preCAM$ID %in% names(table(dat_preCAM$ID))[table(dat_preCAM$ID) == max(table(dat_preCAM$ID))],]

### post-study
# sort(table(dat_postCAM$ID))
sum(table(dat_postCAM$ID) != max(table(dat_postCAM$ID)))
[1] 1
sum(table(dat_postCAM$ID) == max(table(dat_postCAM$ID)))
[1] 192
dat_postCAM <- dat_postCAM[dat_postCAM$ID %in% names(table(dat_postCAM$ID))[table(dat_postCAM$ID) == max(table(dat_postCAM$ID))],]



########################################
# json (from JATOS) to 2D data.frame
########################################
################################ pre-study
### add paradata
tmp_notNumeric <- str_subset(string = colnames(dat_preCAM), pattern = "^meta|^R")
tmp_notNumeric <- str_subset(string = tmp_notNumeric, pattern = "labjs|location", negate = TRUE)

### get survey
vec_ques <- c("PROLIFIC_PID",
              "dummy_informedconsent", 
              "commCheck",
              tmp_notNumeric)

vec_notNumeric = c("PROLIFIC_PID", tmp_notNumeric)

questionnaire_preCAM <- questionnairetype(dataset = dat_preCAM, 
                                        listvars = vec_ques, 
                                        notNumeric = vec_notNumeric, verbose = FALSE)


dim(questionnaire_preCAM)
[1] 193  17
################################ post-study
tmp_numeric <- str_subset(string = colnames(dat_postCAM), pattern = "^nfc")


vec_ques <- c("PROLIFIC_PID", "commCheck",
              "feedCAM_repres", "feedCAM_technicalprobs", "feedCAM_technicalprobsText", "feedCAM_already","feedCAM_alreadyText",
              "openQuestion_MaterialSystem",
              "openQuestion_Ethic",
              "openQuestion_missedPositive", "openQuestion_missedNegative",
              "outcome_research", "outcome_prohibition", "outcome_buy", "outcome_buy_text", 
              "education", "experienceMS",
              tmp_numeric,
              "feedback_critic")

     

vec_notNumeric = c("PROLIFIC_PID", 
                   "feedCAM_technicalprobsText", "feedCAM_alreadyText", 
                                 "openQuestion_MaterialSystem",
                                 "openQuestion_Ethic",
              "openQuestion_missedPositive", "openQuestion_missedNegative",
   "outcome_research", "outcome_prohibition", "outcome_buy", "outcome_buy_text", 
                   "education", "experienceMS",
                   "feedback_critic")

questionnaire_postCAM <- questionnairetype(dataset = dat_postCAM,
                                        listvars = vec_ques,
                                        notNumeric = vec_notNumeric, verbose = FALSE)

questionnaire_postCAM$feedback_critic[questionnaire_postCAM$feedback_critic == ""] <- NA
dim(questionnaire_postCAM)
[1] 192  23
questionnaire_postCAM$multipleEthic <- NA
tmp_multipleEthic <- cbind(dat_postCAM$ID, dat_postCAM$multipleEthic)

questionnaire_postCAM$multiplePositive <- NA
tmp_multiplePositive <- cbind(dat_postCAM$ID, dat_postCAM$multiplePositive)

questionnaire_postCAM$multipleNegative <- NA
tmp_multipleNegative <- cbind(dat_postCAM$ID, dat_postCAM$multipleNegative)


for(i in questionnaire_postCAM$ID){
  # add multipleEthic
  tmp <- tmp_multipleEthic[tmp_multipleEthic[,1] == i, ]
  if(length(unlist(tmp[,2])) == 3){
    questionnaire_postCAM$multipleEthic[questionnaire_postCAM$ID == i] <- paste0(unlist(tmp[,2]), collapse = " \\ ")
  }
  
  # add multiplePositive
    tmp <- tmp_multiplePositive[tmp_multiplePositive[,1] == i, ]
  if(length(unlist(tmp[,2])) == 3){
    questionnaire_postCAM$multiplePositive[questionnaire_postCAM$ID == i] <- paste0(unlist(tmp[,2]), collapse = " \\ ")
  }
    
      # add multipleNegative
    tmp <- tmp_multipleNegative[tmp_multipleNegative[,1] == i, ]
  if(length(unlist(tmp[,2])) == 3){
    questionnaire_postCAM$multipleNegative[questionnaire_postCAM$ID == i] <- paste0(unlist(tmp[,2]), collapse = " \\ ")
  }
}


dim(questionnaire_postCAM)
[1] 192  26
################################ merge two data sets
questionnaire_postCAM$ID <- NULL
questionnaire <- left_join(questionnaire_preCAM, questionnaire_postCAM, by="PROLIFIC_PID")
dim(questionnaire)
[1] 193  41

set up CAM data

pre

Load CAM data

setwd("outputs")
suppressMessages(read_file("CAMdata.txt") %>%
  # ... split it into lines ...
  str_split('\n') %>% first() %>%
    discard(function(x) x == '') %>%
    discard(function(x) x == '\r') %>%
  # ... filter empty rows ...
  discard(function(x) x == '')) -> dat_CAM_pre

raw_CAM <- list()
for(i in 1:length(dat_CAM_pre)){
  raw_CAM[[i]] <- jsonlite::fromJSON(txt = dat_CAM_pre[[i]])
}

Create CAM files, draw CAMs and compute network indicators

########################################
# create CAM single files (nodes, connectors, merged)
########################################
CAMfiles <- create_CAMfiles(datCAM = raw_CAM, reDeleted = TRUE)
Nodes and connectors, which were deleted by participants were removed. 
 # deleted nodes:  0 
 # deleted connectors:  434
## remove white spaces within pre-defined concepts
CAMfiles[[1]]$text <- str_replace_all(string = CAMfiles[[1]]$text, "\\s+", " ")
CAMfiles[[1]]$text <- str_trim(string = CAMfiles[[1]]$text, side = "both")


########################################
# draw CAMs
########################################
CAMdrawn <- draw_CAM(dat_merged = CAMfiles[[3]],
                     dat_nodes = CAMfiles[[1]],ids_CAMs = "all",
                     plot_CAM = FALSE,
                     useCoordinates = TRUE,
                     relvertexsize = 3,
                     reledgesize = 1)
processing 193 CAMs... 
[1] "== participantCAM in drawnCAM"
########################################
# draw CAMs
########################################
tmp_microIndicator <- V(CAMdrawn[[1]])$label # all concepts are pre-defined
networkIndicators <- compute_indicatorsCAM(drawn_CAM = CAMdrawn, 
                                           micro_degree = tmp_microIndicator, 
                                           micro_valence = tmp_microIndicator, 
                                           micro_centr_clo = tmp_microIndicator, 
                                           micro_transitivity = tmp_microIndicator, 
                                           largestClique = FALSE)


########################################
# wordlists
########################################
CAMwordlist <- create_wordlist(
  dat_nodes =  CAMfiles[[1]],
  dat_merged =  CAMfiles[[3]],
  order = "alphabetic",
  splitByValence = FALSE,
  comments = TRUE,
  raterSubsetWords = NULL,
  rater = FALSE
)
[1] "create_wordlist - use raw words"
[1] 0
[1] 6369
[1] "temporarily suffixes are added, because not all words have been summarized"
processing 193 CAMs... 
[1] "== participantCAM in drawnCAM"
DT::datatable(CAMwordlist, options = list(pageLength = 5)) 

plot CAMs using igraph package

Just plot first 10 CAMs for an impression

for(i in 1:10){ # length(CAMdrawn)
  plot(CAMdrawn[[i]], edge.arrow.size = .7,
       layout=layout_nicely, vertex.frame.color="black", asp = .5, margin = -0.1,
       vertex.size = 10, vertex.label.cex = .9)
}

plot aggregated CAM

sel_ids <- unique(CAMfiles[[1]]$participantCAM)
CAMaggregated <- aggregate_CAMs(dat_merged = CAMfiles[[3]], dat_nodes = CAMfiles[[1]],
                                ids_CAMs = sel_ids)
[1] "aggregate_CAMs: using participant CAM ids"
processing 193 CAMs... 
[1] "== participantCAM in drawnCAM"
# plot(CAMaggregated[[2]], vertex.size=diag(CAMaggregated[[1]]) / max(diag(CAMaggregated[[1]]))*20, edge.arrow.size=0.01)
# plot(CAMaggregated[[2]], vertex.size=(abs(V(CAMaggregated[[2]])$value)+1)*5, edge.arrow.size=0.01)


g = CAMaggregated[[2]]
g2 = simplify(CAMaggregated[[2]])
# plot(g2, edge.arrow.size=0.01,
#      vertex.size=diag(CAMaggregated[[1]]) / max(diag(CAMaggregated[[1]]))*20)

E(g2)$weight = sapply(E(g2), function(e) {
  length(all_shortest_paths(g, from=ends(g2, e)[1], to=ends(g2, e)[2])$res) } )
E(g2)$weight = E(g2)$weight * 2
# E(g2)$weight[E(g2)$weight == 1] <- NA

V(g2)$color[V(g2)$value <= .5 & V(g2)$value >= -.5] <- "yellow"

V(g2)$shape <- NA
V(g2)$shape <- ifelse(test = V(g2)$color == "yellow", yes = "square", no = "circle")



### > plot multiple times because of random layout
for(i in 1:3){
  plot(g2, edge.arrow.size = 0,
     layout=layout_nicely, vertex.frame.color="black", asp = .5, margin = -0.1,
     vertex.size=diag(CAMaggregated[[1]]) / max(diag(CAMaggregated[[1]]))*5,
     vertex.label.cex = .9, 
     edge.weight=2, edge.width=(E(g2)$weight/3))
}

save CAMs as .json files, and as .png (igraph)

save_CAMs_as_pictures = FALSE

if(save_CAMs_as_pictures){
  setwd("outputs")

setwd("savedCAMs")
setwd("png")
### remove all files if there are any
if(length(list.files()) >= 1){
  file.remove(list.files())
  cat('\n!
      all former .png files have been deleted')
}

### if no participant ID was provided replace by randomly generated CAM ID

if(all(CAMfiles[[3]]$participantCAM.x == "noID")){
  CAMfiles[[3]]$participantCAM.x <- CAMfiles[[3]]$CAM.x
}

### save as .json files, and as .png (igraph)
ids_CAMs <- unique(CAMfiles[[3]]$participantCAM.x); length(ids_CAMs)


for(i in 1:length(ids_CAMs)){
  save_graphic(filename = paste0(ids_CAMs[i]))
  CAM_igraph <- CAMdrawn[[c(1:length(CAMdrawn))[
    names(CAMdrawn) == paste0(unique(CAMfiles[[3]]$participantCAM.x)[i])]]]
  plot(CAM_igraph, edge.arrow.size = .7,
       layout=layout_nicely, vertex.frame.color="black", asp = .5, margin = -0.1,
       vertex.size = 10, vertex.label.cex = .9)
  dev.off()
}

setwd("../json")
### remove all files if there are any
if(length(list.files()) >= 1){
  file.remove(list.files())
  cat('\n!
      all former .json files have been deleted')
}
for(i in 1:length(raw_CAM)){
  if(!is_empty(raw_CAM[[i]]$nodes)){
    if(nrow(raw_CAM[[i]]$nodes) > 5){
      write(toJSON(raw_CAM[[i]], encoding = "UTF-8"),
            paste0(raw_CAM[[i]]$idCAM, ".json"))
    }
  }
}
}

analyze data

describe data set

feedback to the study

Question:

DT::datatable(questionnaire[,c("PROLIFIC_PID", "feedback_critic")], options = list(pageLength = 5)) 

Material system that has been thought of

Question: Bitte beschreiben Sie an an welches Materialsystem oder welche Materialsysteme Sie dabei gedacht haben.

DT::datatable(questionnaire[,c("PROLIFIC_PID", "openQuestion_MaterialSystem")], options = list(pageLength = 5)) 

basal attributes: most pos. / neg.

Question: Welche drei Begriffen nehmen Sie am positivsten bzw. negativsten für die Beschreibung neuer Materialsysteme wahr?

## most positive
tmp <- str_trim(unlist(str_split(string = questionnaire$multiplePositive, pattern = "\\\\")))
sort(table(tmp))
tmp
 aktive Formänderung durch Umwelteinwirkung 
                                          1 
                         enthält Kunststoff 
                                          1 
                             reaktionsfähig 
                                          1 
                              lebensähnlich 
                                          2 
passive Formänderung durch Umwelteinwirkung 
                                          2 
                              technologisch 
                                          3 
                                    autonom 
                                          8 
                              bioinspiriert 
                                         11 
                         Energie speichernd 
                                         11 
                           widerstandsfähig 
                                         13 
                        Energie generierend 
                                         14 
                              selbstheilend 
                                         15 
                             energieautonom 
                                         16 
                          selbstreparierend 
                                         16 
                            multifunktional 
                                         18 
                                     robust 
                                         20 
                                intelligent 
                                         26 
                               wartungsfrei 
                                         33 
                                zuverlässig 
                                         34 
                           energieeffizient 
                                         37 
                                  langlebig 
                                         39 
                                    haltbar 
                                         43 
                                 ökologisch 
                                         53 
                                 nachhaltig 
                                         54 
                           umweltfreundlich 
                                        105 
## most negative
tmp <- str_trim(unlist(str_split(string = questionnaire$multipleNegative, pattern = "\\\\")))
sort(table(tmp))
tmp
                                    bioinspiriert 
                                                1 
                              Energie generierend 
                                                1 
                                          haltbar 
                                                1 
                                        langlebig 
                                                1 
                                       nachhaltig 
                                                1 
                                   reaktionsfähig 
                                                1 
                                           robust 
                                                1 
                                 widerstandsfähig 
                                                1 
                                      zuverlässig 
                                                1 
                                     wartungsfrei 
                                                2 
                                          autonom 
                                                3 
                                 umweltfreundlich 
                                                3 
       aktive Formänderung durch Umwelteinwirkung 
                                                4 
                                    lebensähnlich 
                                                4 
 aktive Verhaltensänderung durch Umwelteinwirkung 
                                                5 
                                   elektronikfrei 
                                                5 
      passive Formänderung durch Umwelteinwirkung 
                                               14 
passive Verhaltensänderung durch Umwelteinwirkung 
                                               16 
                                 Insekten ähnlich 
                                               19 
                               enthält Kunststoff 
                                               79 
                                leicht zerstörbar 
                                              123 
                                 wartungsintensiv 
                                              130 
                                  umweltschädlich 
                                              160 
## answers of participants
DT::datatable(questionnaire[,c("PROLIFIC_PID", "multiplePositive", "multipleNegative")], options = list(pageLength = 5)) 

any basal attributes missing?

Question: Fallen Ihnen weitere Eigenschaften ein, die Sie als relevant oder negativ für die Beschreibung neuer Materialsysteme erachten, die in der Liste nicht aufgeführt sind, so können Sie diese gerne in folgenden Textfeldern ergänzen:

## answers of participants
DT::datatable(questionnaire[,c("PROLIFIC_PID", "openQuestion_missedPositive", "openQuestion_missedNegative")], options = list(pageLength = 5)) 

basal attributes: ethical most relevant

Question: Welche drei Begriffe sind aus Ihrer Sicht in moralischer Hinsicht am “relevantesten”?

## ethical relevant
tmp <- str_trim(unlist(str_split(string = questionnaire$multipleEthic, pattern = "\\\\")))
sort(table(tmp))
tmp
       aktive Formänderung durch Umwelteinwirkung 
                                                1 
      passive Formänderung durch Umwelteinwirkung 
                                                1 
passive Verhaltensänderung durch Umwelteinwirkung 
                                                1 
                                 widerstandsfähig 
                                                1 
                                   elektronikfrei 
                                                2 
                                selbstreparierend 
                                                2 
                                    technologisch 
                                                2 
 aktive Verhaltensänderung durch Umwelteinwirkung 
                                                3 
                                leicht zerstörbar 
                                                3 
                                   reaktionsfähig 
                                                3 
                                           robust 
                                                3 
                                  multifunktional 
                                                4 
                               enthält Kunststoff 
                                                5 
                               Energie speichernd 
                                                7 
                                   energieautonom 
                                                8 
                                 Insekten ähnlich 
                                                8 
                                    selbstheilend 
                                                9 
                                     wartungsfrei 
                                                9 
                                          autonom 
                                               11 
                                    bioinspiriert 
                                               14 
                              Energie generierend 
                                               14 
                                      intelligent 
                                               17 
                                    lebensähnlich 
                                               18 
                                          haltbar 
                                               19 
                                      zuverlässig 
                                               21 
                                  umweltschädlich 
                                               23 
                                        langlebig 
                                               32 
                                 energieeffizient 
                                               41 
                                       ökologisch 
                                               77 
                                       nachhaltig 
                                               93 
                                 umweltfreundlich 
                                              124 
## answers of participants
DT::datatable(questionnaire[,c("PROLIFIC_PID", "multipleEthic")], options = list(pageLength = 5)) 

argument for choosen basal attributes

Question: Bitte begründen Sie kurz die Auswahl der ethisch relevanten Begriffe:

## answers of participants
DT::datatable(questionnaire[,c("PROLIFIC_PID", "openQuestion_Ethic")], options = list(pageLength = 5)) 

outcome questions

Question: Sollte die Entwicklung innovativer Materialsysteme mit öffentlichen Mitteln gefördert werden?

table(questionnaire$outcome_research)

    no unsure    yes 
     4     32    156 

Question: Sollten die Erforschung und Entwicklung solcher innovativer Materialsysteme verboten werden?

table(questionnaire$outcome_prohibition)

    no unsure    yes 
   182      7      3 

Question: Wären Sie bereit, Produkte zu kaufen, die innovative Materialsysteme enthalten?

table(questionnaire$outcome_buy)

    no unsure    yes 
     2     85    105 

if yes to previous question

Question: An welche möglichen Produkte haben Sie gedacht?

## answers of participants
DT::datatable(questionnaire[,c("PROLIFIC_PID", "outcome_buy_text")], options = list(pageLength = 5)) 

co-variation of basal attributes

Compare the probability that two concepts are connected in randomly generated networks to drawn CAMs:

## get average number of drawn concepts (here fixed)
numConcepts <- mean(networkIndicators$num_nodes_macro)
## get average density
numDensity <- mean(networkIndicators$density_macro)

## simply get the average probability that two concepts are connected:
g <- igraph::random.graph.game(n = numConcepts, p.or.m = numDensity)
plot(g)

are.connected(g, 1, 2)
[1] FALSE
#> whereby each edge to be drawn has the identical probability in the Erdős–Rényi model
vec_booleanConnected <- c()
# vec_booleanConnected2 <- c()

for(i in 1:10000){
  g <- igraph::random.graph.game(n = numConcepts, p.or.m = numDensity)
  vec_booleanConnected[i] <- are.connected(g, 1, 2)
    # vec_booleanConnected2[i] <- are.connected(g, 22, 26)
}
baselineProbability <- mean(vec_booleanConnected)
baselineProbability
[1] 0.0402
# mean(vec_booleanConnected2)

This baseline probability can be compared to all possible combinations of drawn concepts:

vec_boolean <- c()
for(i in 1:length(CAMdrawn)){
  vec_boolean[i] <- are.connected(graph = CAMdrawn[[i]], 
              v1 = V(CAMdrawn[[i]])[V(CAMdrawn[[i]])$label == "robust"], 
              v2 = V(CAMdrawn[[i]])[V(CAMdrawn[[i]])$label == "widerstandsfähig"])
}

mean(vec_boolean)
[1] 0.1709845