2

To make a struct's members "private" to the outside I know that I can do this.

In the .h file

typedef struct Obj Obj;

In the .c file you then

struct Obj {
int a;
int b;
}

This will keep the knowledge of the existense of a and b from beeing known. But all the "member" functions in the .c file will now about them and can opperate on then. But what I wonder about now is that if you can make PART of the struct "private". Say that I want to keep those a and b variables "private" but then I want to have some function pointers that I want to remain public. Is this possible? I know that if I try to declare these in the struct in the .h file I would get a duplicate declaration error on the struct.

inquam
  • 12,664
  • 15
  • 61
  • 101
  • 5
    Please do not waste time on this. Please use C++ if you think you need private. Almost all C compilers are C/C++ compilers. Just switch and save yourself a lot of wasted time. – S.Lott Jul 23 '10 at 10:14
  • 1
    The notion of private/public members does not exist in (current) C structs. – Michael Foukarakis Jul 23 '10 at 10:16
  • 1
    @S.Lott: If I wasn't in an ANSI C ONLY enviroment I would do that. But since I'm locked to ANSI C I can't. Otherwise this question would not have come up. – inquam Jul 23 '10 at 10:27
  • @inquam: Nothing wrong with ANSI C. What's wrong is the notion of 'private'. You did not say "ANSI C OR DIE" in the question, so there's no way to know what's fixed and what's flexible. Since ANSI C appears fixed -- only based on the comment, not the question -- then private cannot be done. We can't guess what choices are available to you, and you didn't say that ANSI C was a requirement. – S.Lott Jul 23 '10 at 10:34
  • If you can't work in C++, I'd suggest working to the conventions of C. There's no such thing as private in C, so don't try to use it. Trying to cram your favourite square-peg paradigm into your current round-hole language will only frustrate whoever maintains the project later. – Ant Jul 23 '10 at 10:35
  • 1
    That private does not exist I know, that is the reason for refering to it as "private". What I wanted to do was mimic behaviour of classes, as much as possible, using ANSI C. Many people before me working on this project have already implemented pseudo OO in many different ways. What I wanted to do was to use on consistent way of doing it. Many things in the project is perfectly suited for OO, but a company decision is to only allow ANSI C. OO or not has not been a question. I might not agree with that decision, but I will follow it. Private variables member functions etc can all be mimiced. – inquam Jul 23 '10 at 10:42
  • It's worth pointing out that C++ doesn't actually have encapsulation (the enforced kind) either. As long as there are unsafe pointers, you can get to pretty much anything. And as long as there are terrible coders, you can't assume it hasn't been done. – nmichaels Jul 23 '10 at 10:45
  • @inquam: Your comment fundamentally changes your question. "What I wanted to do was to use on consistent way of doing it". Please update your question to say what you **really** want. – S.Lott Jul 23 '10 at 11:05
  • @S.Lott: I don't think it does. I want to "mimic classes" using ANSI C. Then the reason for that is that I want a consitent way of doing it accross the project and not ten different ways cooked up be everyone. By asking here I excpected to get some input on how to do it and from that decide which route would be best suited for the project. But the reason for me wanting to "mimic classes" using ANSI C is actually not the question. – inquam Jul 23 '10 at 11:17
  • @inquam: "But the reason for me wanting to "mimic classes" using ANSI C is actually not the question". That's often a mistake. Your real reason is your real question. Many alternative solutions are attractive nuisances. If you ask your real question, you may get answers that you didn't think of. – S.Lott Jul 23 '10 at 11:40

2 Answers2

3

Copy Python: use the honour system for ‘private’ members.

Put a _ at the start of the member name as a red flag that other code shouldn't be touching it. Unless you've got security boundaries inside your application (which is uncommon), you don't actually need real privates, you only need a convention agreed-upon by members of your team to pretend they're private.

Try not to add complexity by forcing C into a paradigm which it doesn't really fit. Extra headers for public/private interfaces and extra source files for class management are going to make your development work more complicated, defeating the ‘more maintainable’ goal that information-hiding is aiming for.

bobince
  • 528,062
  • 107
  • 651
  • 834
  • That would work great. But here it's a question of different type of objects that might all look totaly different, but all have in common that they have a run function. That function always take the same arguments but can have totaly different implementations. Thus it would make sense to be able to only expose that run function and the letting the individual objects handle how and with what they "run". But you are right, it's a possibility and if nothing else comes up I might very well go that route. Thanx. – inquam Jul 23 '10 at 10:50
2

Could this (not tested or even compiled) work for you?

in the file "everybody_includes_me.h":

typedef public_struct {
  func1_ptr;
  func2_ptr;
} PUBLIC_STRUCT;

extern PUBLIC_STRUCT func_pointers;

and in the file "totally_public.c":

PUBLIC_STRUCT func_pointers;

then in the file "all_private.c":

struct Obj {
  PUBLIC_STRUCT *func_pointers;
  int a;
  int b;
}
Pete Wilson
  • 8,610
  • 6
  • 39
  • 51
  • 1
    Was thinking about the same thing, having a struct with the functionpointers... I'll give it a try and see. – inquam Jul 23 '10 at 10:28
  • Just remember to pass an instance of struct Obj to your functions when they're called. That, or you could implement your own currying in C. – nmichaels Jul 23 '10 at 10:47