Использование циклов for и If в R для преобразования данных

Я пытаюсь преобразовать свою матрицу в другой формат в R, но, поскольку у меня нет большого опыта кодирования с циклами for / if, я терплю неудачу. Любая помощь приветствуется.

Демонстрация моей матрицы выглядит следующим образом:

S   K1  K1  K2  K2  K3  K3  K4  K4  K5  K5   
1   A   P   A   A   A   A   P   A   A   A   
2   A   A   A   A   A   A   A   A   P   P   
3   A   P   A   A   A   A   P   A   A   A   
4   A   P   A   A   A   A   P   A   A   A   
5   A   P   A   A   A   A   A   A   P   A

A = ОТСУТСТВУЕТ P = ПРИСУТСТВУЕТ

Я хотел бы получить имена столбцов для существующих столбцов и распечатать их. Каждый образец имеет 2 столбца P. Итак, конечный результат должен быть

S   V1  V1  
1   K1  K4      
2   K5  K5      
3   K1  K4      
4   K1  K4  
5   K1  K5  

Я знаю, что это простой цикл for / if, но я не могу найти решение. У вас есть коды, чтобы это исправить?

Что именно вы пробовали? Действительно ли ваши данные находятся в матрице или в data.frame?

MrFlick 01.05.2018 22:15

у вас есть столбец с таким же названием? И почему вы решили, что вам здесь нужна петля? Я бы пошел с indx <- which(df == "P", arr.ind = TRUE) ; matrix(colnames(df)[indx[order(indx[, "row"]), "col"]], ncol = 2, byrow = TRUE) (если df - ваш фрейм данных / матрица)

David Arenburg 01.05.2018 22:20

Спасибо за вашу помощь! У меня есть столбцы с таким же названием. Я решил использовать цикл, потому что я не знаком с r и думаю как сценарий оболочки. Итак, могу ли я использовать это с теми же именами столбцов или мне нужно их изменить?

Mystra 01.05.2018 22:27

Вы пробовали мой код?

David Arenburg 01.05.2018 23:01

Я пытался. На самом деле это то, что я хотел, но я не могу распечатать результат в формате .txt или .csv, поскольку это индекс. Есть ли способ обойти это?

Mystra 01.05.2018 23:40
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
5
80
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Одним из множества доступных вариантов может быть:

df_res <- cbind(df[1],t(apply(df[-1], 1, function(x)names(df)[which(x= = "P")+1])))

#write result to a csv file
write.csv(df_res, file = "d:\\MyData.csv",row.names=FALSE)

#   S  1  2
# 1 1 K1 K4
# 2 2 K5 K5
# 3 3 K1 K4
# 4 4 K1 K4
# 5 5 K1 K5

Мне просто интересно, как OP создал такую ​​матрицу / data.frame.

Данные:

df <- read.table(text = 
"S   K1  K1  K2  K2  K3  K3  K4  K4  K5  K5   
1   A   P   A   A   A   A   P   A   A   A   
2   A   A   A   A   A   A   A   A   P   P   
3   A   P   A   A   A   A   P   A   A   A   
4   A   P   A   A   A   A   P   A   A   A   
5   A   P   A   A   A   A   A   A   P   A",
header = TRUE, stringsAsFactors = FALSE)

#Change the name of columns 
names(df) <- sub("(.*)\\.\\d+","\\1",names(df))

Кстати, теперь я заметил, что R не разрешал иметь столбцы с одинаковыми именами, и мои имена столбцов - K1, K1.1, K2, K2.2 ... Я тот нуб!

Mystra 01.05.2018 22:38

@Mystra Но вы можете изменить имена столбцов с помощью names(df). Если вы заметили, что я изменил его в data с помощью names(df) <- c('S','K1', 'K1', 'K2', 'K2', 'K3', 'K3', 'K4', 'K4', 'K5', 'K5'), вы можете попробовать это со своей стороны.

MKR 01.05.2018 22:40

@Mystra Не беспокойся. обучение - это процесс, требующий времени. В какой-то момент каждый был новичком.

MKR 01.05.2018 22:41

Это довольно уродливо, но это добавит .1 к именам каждого столбца с нечетным номером в вашем фрейме данных: names(df[seq.int(ncol(df))%%2 == 0]) <- paste0(names(df[seq.int(ncol(df))%%2 == 0]), '.1')

divibisan 01.05.2018 22:50

@Mystra Какие у вас сейчас названия столбцов? Я уверен, что мы легко разберемся. Просто дайте мне знать 10-20 названий столбцов.

MKR 01.05.2018 22:56

Я пробовал colnames (df) <- gsub (". 1", "", colnames (df)), но это не сработало ..

Mystra 01.05.2018 22:59

@Mystra Я изменил свой ответ, включив способ изменения имени столбца. В основном это names(df) <- sub("(.*)\\.\\d+","\\1",names(df))

MKR 01.05.2018 23:02

Ваш код работал у меня очень хорошо, единственная проблема в том, что я не могу использовать write.txt для получения данных. Есть ли какой-нибудь способ для этого?

Mystra 01.05.2018 23:43

csv в порядке, я думаю

Mystra 01.05.2018 23:53

@Mystra Я обновил свой ответ, включив в него код для записи в файл. Имя файла выбрали как d:\\MyData.csv. Вы можете выбрать по своему усмотрению.

MKR 01.05.2018 23:58
Ответ принят как подходящий

вы можете использовать data.table

library(data.table)
setDT(melt(df,1))[value= = "P"][order(S),as.list(sub("[.].*","",variable)),by=S]
   S V1 V2
1: 1 K1 K4
2: 2 K5 K5
3: 3 K1 K4
4: 4 K1 K4
5: 5 K1 K5

Очень красивое решение. Если скорость или память вызывают беспокойство, использование setDT перед melt поможет.

IceCreamToucan 01.05.2018 23:07

Вроде неплохо, но я получил сообщение об ошибке «Ошибка в eval (.massagei (isub), x, parent.frame ()): объект 'value' не найден»

Mystra 01.05.2018 23:42

как называются имена столбцов при запуске setDT(melt(df,1))?

Onyambu 01.05.2018 23:48

0101, 0101, 0102, 0102, 0201, 0201 ... 596 столбцов с разными именами

Mystra 01.05.2018 23:54

у меня вопрос, когда вы запускаете a=setDT(melt(df,1));names(a), что вы получаете ??

Onyambu 01.05.2018 23:57

"sample.id" "0101" "0101" "0102" "0102" "0103" "0103" "0201" "0201" "0202" в основном имена моих столбцов

Mystra 02.05.2018 00:01

в тот момент, когда вы расплавите свои данные, вы должны иметь их в длинном формате, таким образом, у вас будет три столбца.

Onyambu 02.05.2018 00:03

Получил вот что: "sample.id" "переменная" "значение"

Mystra 02.05.2018 00:12

поэтому, когда я сделал = setDT (melt (hla_a, 1)) [value == "P"] [order (sample.id), as.list (‌ sub ("[.]. *", "", varia‌ble)), by = sample.id] я получил ошибку: 'Ошибка в [.data.table (setDT (melt (hla_a, 1)) [value == "P"], order (sample.id),: j doesn 't оценивает одинаковое количество столбцов для каждой группы'

Mystra 02.05.2018 00:14

Хорошо, как вы можете сказать, есть столбец под названием value, теперь вы можете попробовать a[value= = "P"][order(sample.id),as.list(sub("[.].*","",variab‌​le)),by=sample.id]

Onyambu 02.05.2018 00:15

та же ошибка: ошибка в [.data.table (a [value == "P"], order (sample.id), as.list (sub ("[.]. *",: j не соответствует тому же количеству столбцов) для каждой группы

Mystra 02.05.2018 00:19

mhh .. Это означает, что есть другие строки с большим количеством "P", чем другие

Onyambu 02.05.2018 00:20

вы можете сделать что-то вроде b=a[value= = "P"][order(sample.id),.(V1=sub("[.].*","",variabl‌​e),V2=sequence(.N)),‌​by=sample.id];dcast(‌​b,S~V2,value.var = "V1",fill=NA)

Onyambu 02.05.2018 00:26

Другие вопросы по теме