Register a SA Forums Account here!
JOINING THE SA FORUMS WILL REMOVE THIS BIG AD, THE ANNOYING UNDERLINED ADS, AND STUPID INTERSTITIAL ADS!!!

You can: log in, read the tech support FAQ, or request your lost password. This dumb message (and those ads) will appear on every screen until you register! Get rid of this crap by registering your own SA Forums Account and joining roughly 150,000 Goons, for the one-time price of $9.95! We charge money because it costs us money per month for bills, and since we don't believe in showing ads to our users, we try to make the money back through forum registrations.
 
  • Post
  • Reply
InAndOutBrennan
Dec 11, 2008
I'm tooling around with C++, mostly trying to learn stuff.

Suppose I would want to test if I'm out of bounds of my allocated array, is this ok?

code:
{
  char *test = new char[10];
  char *end;
  end = test + 10;
  
  char *curpos;
}
End would point to an address outside of the allocated memory and I could check this by:

code:
{
  if(curpos == end)
  {
  //sort it out
  }
}
Is there any case where actually trying to set or access the address of end would be illegal?

edit: I could of course check for the last position in the allocated array instead but I'm curious.

Adbot
ADBOT LOVES YOU

InAndOutBrennan
Dec 11, 2008
Allright, thanks!

InAndOutBrennan
Dec 11, 2008
Can anyone recommend a CSV-parser function/library that has no problem chewing through gigabyte size files without loading the whole thing into memory?

I'm tinkering around with my own but it seems to me that this problem should be solved by now.

Thanks.

InAndOutBrennan
Dec 11, 2008
I'm probably missing something.

Say I have a class with a method. When I set up the class, at runtime I want the method to do either something A or something B. But I want it to do the same thing every time.

Pseudocode:
code:
bool quoted;

if(user_input) {
	quoted = false;
} else {
	quoted = true
}

my_reader = new CSVReader(quoted);
my_reader.get_row();
Depending on the value of quoted I want get_row() to do different things without having to if() stuff in the method every time i call it. I looked at function/method pointers but that seemed overly complicated.

I can solve it by making two different classes inherit from a base class but I'm curious as to if it's possible some other way?

InAndOutBrennan
Dec 11, 2008

brosmike and Dicky B posted:

...

Thanks!

I'm mostly using this as a learning/experimenting thing and CSV-files is something I'm familiar with and do a lot of work with so that's why I'm using them as subject matter.

Regarding the other things (separator, column names etc), those are common to both cases so I have to take care of them regardless.

I'll poke around the stuff you mentioned and see what I can pick up.

InAndOutBrennan
Dec 11, 2008
If I have a vector<vector<char> > and do a push_back with a new vector<char>.

Will that invalidate any vector<char>::iterators to previously stored content?

InAndOutBrennan
Dec 11, 2008
It compiles fine here but it segfaults when run so it seems the iterators are invalidated. I suspected as much, thanks for the help.

Bugger.

(was at work when posting the question, with no compiler in sight)

InAndOutBrennan
Dec 11, 2008

Gerblyn posted:

You could just use vector<vector<char>*> (or smart pointers) with dynamically allocated vector<char>s instead, your iterators would be fine then.

prolecat posted:

If instead you stored pointers to the nested vectors, their iterators would be safe since their contents wouldn't be moved around when the containing vector was reallocated.

Yeah this is probably the way I'm heading. Thanks again.

InAndOutBrennan
Dec 11, 2008
The below works fine as long as I keep it in my main but as soon as I try to move it to a function it leads to not being able to bind to the statement further down.

The work I try to do:

code:
sqlite3_stmt *sql_insert_stmt;

std::string query_str = "INSERT INTO test VALUES(";
for(unsigned long long i = 0; i < num_columns; ++i) {
	query_str += "?, ";
}
query_str.resize(query_str.size()-2);
query_str += ")";

rc = sqlite3_prepare_v2(sqldb
			,query_str.c_str()
			,-1
			,&sql_insert_stmt
			,NULL);

if(rc != SQLITE_OK) {
	std::cout << "Could not prepare" << std::endl;
}
Code would just be copied pasted in to the function below with small changes in varnames and added return statements.

code:
int create_insert_statement(sqlite *sqldb, sqlite3_stmt *sql_stmt, int num_columns) {
...
}
And called with (sqldb and num_columns are intialized earlier):
code:
sqlite3_stmt *sql_insert_stmt;
create_insert_statement(sqldb, sql_insert_stmt, num_columns);
Guesses:
1. I'm not preparing the statement I think I'm preparing when I pass the pointer to the sqllite3_stmt? SQLite is not complaining so far though.
2. If not the above then it's something to do with the statement needing to remember the query text and that goes out of scope when the function exits. This would mean that it working for me is purely coincidental since I'm reusing the same std::string multiple times.

InAndOutBrennan fucked around with this message at 12:50 on Dec 30, 2012

InAndOutBrennan
Dec 11, 2008

nielsm posted:

...awesome...

Well, that did the trick! Thanks! Sorry for not posting all of it but I figured I got the important bits in there.

As soon as I think I get those loving pointers down...

InAndOutBrennan
Dec 11, 2008
In an effort to put together a simple hobby project with "proper" composition for once I'm passing structs around a lot more than I have before (granted I'm a lovely C-programmer but we're here to learn right?).

I'm a bit confused as to why this works. I would assume that I'd need to malloc the struct somewhere?

Should I? What happens if I do, what happens if I don't?

Thanks.

code:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

struct stuff {
	char *stuff_in_stuff;

	int c;
};

int do_stuff(struct stuff *s) {
	s->stuff_in_stuff = malloc(sizeof(char) * 1024);
	strncpy(s->stuff_in_stuff, "Hello stuff!", 1024-1);

	s->c = 15;

	return 0;	
}

int main(void) {
	struct stuff *s;

	do_stuff(s);

	printf("%s\n", s->stuff_in_stuff);
	printf("%d\n", s->c);

	return 0;
}

InAndOutBrennan
Dec 11, 2008
"Proper composition" just means that I try to put together stuff in a nicer way instead of just writing hugeass functions that do 100 things at once. Thus passing around data a lot more than I'm used to.

Problem is that it compiles, runs and produces the "desired" result. But in this case this is just luck? As I said I expected to have to do it and was surprised when everything "worked" without it. Running with valgrind does indeed generate a warning about uninitialized pointers.

Thanks.

sarehu posted:

...good stuff..

Adbot
ADBOT LOVES YOU

InAndOutBrennan
Dec 11, 2008
Just random thoughts from a hobby c++ writer here. My production code tends to be written in stuff you would expect in the data place.

But poo poo is it interesting to dip in and out every 6 months to learn something new. Looking at some code I have in both python and C++ the difference is really minimal in structure these days.

15 years ago it would have needed so many "helper" functions and classes that now are part of the std.

Yes you can dip down and roll your own poo poo when needed but from someone where every project is greenfield it's just so nice these days.

TLDR: Haven't used new or malloc in ages. And yes I understand, different strokes.

  • 1
  • 2
  • 3
  • 4
  • 5
  • Post
  • Reply