-1

When I try to assign a value to an array using pointers, I am getting an error that float[int] is not a valid type.

This is my code, it takes a text file that has:

1 0.005
2 0.025
3 0.01
#include <iostream>
#include <fstream>
using namespace std;
string filename;

int number_of_cells(string filename);
void read(string filename,int i,float *id_area);

int id;     //int column;
float area; //double tarea;

int main()
{
    string file_name="id-area-3.txt";
    int ncell = number_of_cells(file_name);
    cout<<" Number of lines are "<<ncell<<"\n";
    float id_area[ncell][2];
    read(file_name,ncell,*id_area);
}

int number_of_cells(string filename)
{
    int it = 0;
    ifstream theFile(filename);

    while (theFile>>id>>area)
    {
        it++;
    }

    return(it);
}

void read(string filename,int i,float *id_area)
{
    ifstream theFile(filename);
    int j = 0;

    while (theFile >> id >> area)
    {
        cout<<" ID:" << id << " , " << " area: " <<area << "|"<<"\n";

        for (j=1;j<i;j++)
        {
            id_area[j][0]=id;
            id_area[j][1]=area;
            j++;
        }
    }

    //cout<<typeid(arr).name();
}

I get this error:

====================[ Build | Laser_ablation_nanoparticles | Debug ]============
"C:\Program Files\JetBrains\CLion 2023.1.5\bin\cmake\win\x64\bin\cmake.exe" --build C:\Users\Vishal\CLionProjects\Laser_ablation_nanoparticles\cmake-build-debug --target Laser_ablation_nanoparticles -j 6
[1/2] Building CXX object CMakeFiles/Laser_ablation_nanoparticles.dir/main.cpp.obj
FAILED: CMakeFiles/Laser_ablation_nanoparticles.dir/main.cpp.obj 
C:\PROGRA~1\JETBRA~1\CLION2~1.5\bin\mingw\bin\G__~1.EXE  -I"C:/Users/Vishal/Documents/Academic documents/MSc/Manchester/dissertation/Eigen/eigen-3.4.0" -g -fdiagnostics-color=always -std=gnu++23 -MD -MT CMakeFiles/Laser_ablation_nanoparticles.dir/main.cpp.obj -MF CMakeFiles\Laser_ablation_nanoparticles.dir\main.cpp.obj.d -o CMakeFiles/Laser_ablation_nanoparticles.dir/main.cpp.obj -c C:/Users/Vishal/CLionProjects/Laser_ablation_nanoparticles/main.cpp
C:/Users/Vishal/CLionProjects/Laser_ablation_nanoparticles/main.cpp: In function 'void read(std::string, int, float*)':
C:/Users/Vishal/CLionProjects/Laser_ablation_nanoparticles/main.cpp:45:**23: error: invalid types 'float[int]' for array subscript
   45 |             id_area[j][0]=id;
      |                       ^
C:/Users/Vishal/CLionProjects/Laser_ablation_nanoparticles/main.cpp:46:23: error: invalid types 'float[int]' for array subscript
   46 |             id_area[j][1]=area;
      |                       ^**
ninja: build stopped: subcommand failed.
marc_s
  • 732,580
  • 175
  • 1,330
  • 1,459
  • Your function `read()` takes a `float*` as argument. In the `for` loop, you access `f[j][0]` and `f[j][1]`. `f[j]` already is a `float`, so you cant use `operator[]` on it again. – Joel Aug 15 '23 at 11:12
  • 1
    You pass a pointer to a float to the function.That parameter is not a 2D array. – BoP Aug 15 '23 at 11:13
  • 5
    The parameter should be `float id_area[][2]` – paddy Aug 15 '23 at 11:14
  • 2
    Why is the use of pointers so important to you? if at all possible just try to avoid them? When reading files you could make a struct for your data e.g `struct my_data { int id1; float f1; int id2; float f2; int id3; float f3;}` and then build up a `std::vector` by loading the data and pushing back one such struct for each line read. It will work much nicer and you will not get memory leaks or invalid pointers to worry about. – Pepijn Kramer Aug 15 '23 at 11:24
  • 3
    `float id_area[ncell][2];` by the way is NOT standard C++ (compile with -Wpedantic) since `ncell` is not a compile time constant (another reason to use std::vector). Side note : stop using `using namespace` – Pepijn Kramer Aug 15 '23 at 11:24
  • 1
    [Why is "using namespace std;" considered bad practice?](https://stackoverflow.com/questions/1452721/why-is-using-namespace-std-considered-bad-practice) – Jesper Juhl Aug 15 '23 at 11:26
  • 2
    Global variables? Why? – Jesper Juhl Aug 15 '23 at 11:26
  • 1
    @JesperJuhl I just think OP is inexperienced (at least in C++) – Pepijn Kramer Aug 15 '23 at 11:27
  • 1
    @PepijnKramer Probably. It's still a bad idea though. – Jesper Juhl Aug 15 '23 at 11:28
  • 2
    Note: Pointers are not arrays. Arrays are not pointers. C-style arrays are usually a bad idea (forget they exist) - use `std:.array` or `std::vector`. – Jesper Juhl Aug 15 '23 at 11:32
  • @pepijnKramer, I will try with structs then. because in y real file i would have around a 1000 lines, i think i don't want any leaked memory – Vishal Patil Aug 15 '23 at 11:36
  • Since the error message can be a bit mysterious: it's trying to say that `id_area[j]` is a `float`, and `0` is an `int` - thus `id_area[j][0]` has the form `float[int]`. `id_area[j]` is a `float` because `id_area` is a `float*`. You can't index a `float`. – molbdnilo Aug 15 '23 at 12:25

2 Answers2

0

In C++ I would expect your code to look somewhat like this : Note I used a stringstream to mimic your file (easier to test that way)

#include <iostream>
#include <fstream>
#include <sstream>
#include <vector>

struct cell_t
{
    int id;
    float area;
};

auto load(std::istream& is)
{
    std::vector<cell_t> cells;
    int id;
    float area;
    while ( is >> id >> area )
    {
        cells.push_back(cell_t{id,area});
    }
    return cells;
}


int main()
{
    std::istringstream is {"1 0.005 2 0.025 3 0.01"};
    //std::ifsteam is{"id-area-3.txt"}

    auto cells = load(is);
    for(const auto& cell : cells)
    {
        std::cout << "Cell id = " << cell.id << ", area = " << cell.area <<"\n";
    }

    return 0;
}
Pepijn Kramer
  • 9,356
  • 2
  • 8
  • 19
0

The error

invalid types 'SomeTypeHere[int]' for array subscript

means you tried array-access on something twice, when you can only do it once. If you have a variable float* my_array, you can say my_array[123] (or any other number, but you can't say my_array[123][45] (or any other number). That's because after you've used the subscript once, i.e. my_array[123] - what you have is a float: you "dereferenced", removed the *, once, and now the float * becomes float. And you can't take some float value and subscript it, i.e. 5.448[45] is meaningless. That's what the compiler is trying to tell you.

It's true that this error description is not very novice-friendly!


Just for comparative reference, G++ says something very similar:

<source>:45:23: error: invalid types 'float[int]' for array subscript
   45 |             id_area[j][0]=id;
      |                       ^

and clang++ says:

<source>:45:23: error: subscripted value is not an array, pointer, or vector
            id_area[j][0]=id;
            ~~~~~~~~~~^~
einpoklum
  • 118,144
  • 57
  • 340
  • 684