rgdata

R write.fwf(): receiving error message when using imported data


I'm starting to learn R, and I don't understand an error message I am receiving from write.fwf() from the gdata package. I created a two data files, one using the following code:

testdata <- data.frame (VAR1=c(1),
                         VAR2=c(2))

And another from importing a test .csv file:

VAR1,VAR2
1,2

My full code is:

library(tidyverse)  # Loads the `tidyverse` collection
library(readxl)     # Reads CSV and Excel files
library(gdata)      # For write.fwf
testdata <- data.frame (VAR1=c(1),
                         VAR2=c(2))
read_testdata <- read_csv ("test.csv")

write.fwf(x=testdata)
write.fwf(x=read_testdata)

The two data frames seem identical to me. When I run write.fwf(x=testdata), the function returns successfully:

> write.fwf(x=testdata)
VAR1 VAR2
1 2

However when I use the imported version of the data by running write.fwf(x=read_testdata), I get the following error message:

Error in `[<-`:
! Assigned data `format(...)` must be compatible with existing data.
✖ Existing data has 1 row.
✖ Assigned data has 4 rows.
ℹ Row updates require a list value. Do you need `list()` or `as.list()`?
Caused by error in `vectbl_recycle_rhs_rows()`:
! Can't recycle input of size 4 to size 1.
Run `rlang::last_trace()` to see where the error occurred.
Warning message:
In x2[!test] <- format(y[!test, i], justify = justify, width = tmp,  :
  number of items to replace is not a multiple of replacement length

I don't understand what this error message means. I tried to simplify the inputs as much as I could to see where the two inputs differ, but I'm still not seeing what is causing the error. Do I need to process the imported data somehow before using it in write.fwf()? Any insight is appreciated. Thank you.


Solution

  • The read_csv function imports the data as a tibble, and write.fwf requires a data.frame.

    You can try to import your CSV file with read.csv instead, it will be imported as a data.frame:

    read_testdata2 <- read.csv("test.csv")
    write.fwf(x=read_testdata2)
    

    Or as proposed by @margusl, first convert the tibble to a data.frame:

    df = as.data.frame(read_testdata)
    write.fwf(x=df)
    

    You can check that the objects have different classes with:

    class(testdata)
    class(read_testdata)