SitePoint Sponsor

User Tag List

Page 2 of 3 FirstFirst 123 LastLast
Results 26 to 50 of 62
  1. #26
    SitePoint Addict bronze trophy
    Join Date
    Apr 2013
    Location
    Ithaca
    Posts
    338
    Mentioned
    6 Post(s)
    Tagged
    1 Thread(s)
    Looks like PHP developers have rejected the idea of metaprogramming, at least with runkit ever making it to the core of PHP. This is too bad, but hey at least I was courageous enough to actually write a feature request ticket to PHP, and someone took the time and trouble to respond. XD

    https://bugs.php.net/bug.php?id=65459

    Perhaps I should try namespace wildcard import next time? Although the chance of each feature request gets approved is low, there is a fair chance for at least one of all those requests being accepted if all of them reach PHP developers.

  2. #27
    Barefoot on the Moon! silver trophy
    Force Flow's Avatar
    Join Date
    Jul 2003
    Location
    Northeastern USA
    Posts
    4,516
    Mentioned
    51 Post(s)
    Tagged
    1 Thread(s)
    Quote Originally Posted by asp_funda View Post
    You have to define a const with class definition and its value can't be changed. Read-only on the other hand can be set in a method (its rw within the class) but is read-only when accessed outside the class. That would definitely bring down the usage of getters.
    Ok, in that case:

    PHP Code:
    class thing {
        private 
    $attribute null;

        function 
    __construct($attr){
             
    $this->attribute=$attry;
        }

        function 
    getAttribute(){
             return 
    $this->attribute;
         }
    }

    $newthing = new thing('something');
    echo 
    $newthing->getAttribute(); 
    That essentially allows you to set the variable once, and get it at any time.


    Quote Originally Posted by Hall of Famer View Post
    Good point. Also const does not accept arrays or objects, it only works for numbers, booleans and strings.
    You could use serialize/unserialize to shoehorn arrays and objects into a const.
    Visit The Blog | Follow On Twitter
    301tool 1.1.5 - URL redirector & shortener (PHP/MySQL)
    Can be hosted on and utilize your own domain

  3. #28
    SitePoint Addict bronze trophy
    Join Date
    Apr 2013
    Location
    Ithaca
    Posts
    338
    Mentioned
    6 Post(s)
    Tagged
    1 Thread(s)
    Quote Originally Posted by Force Flow View Post
    You could use serialize/unserialize to shoehorn arrays and objects into a const.
    Umm this... I thought PHP class constants must be declared and defined upon you write the class? Is it even possible to do this?

    PHP Code:
    class MyClass{
        const 
    constObject;

        public function 
    __construct(Object $object){
            
    self::constObject serialize($object);
        }

    Otherwise, you will have to actually know the serialized string representation for the array or object, not a good idea I guess...

  4. #29
    Barefoot on the Moon! silver trophy
    Force Flow's Avatar
    Join Date
    Jul 2003
    Location
    Northeastern USA
    Posts
    4,516
    Mentioned
    51 Post(s)
    Tagged
    1 Thread(s)
    Quote Originally Posted by Hall of Famer View Post
    Umm this... I thought PHP class constants must be declared and defined upon you write the class? Is it even possible to do this?
    Yep, they have to be defined upon initialization. If you want to set a variable just once, you'll likely have to use something similar to the example I provided.

    Otherwise, you will have to actually know the serialized string representation for the array or object, not a good idea I guess...
    No, it's no ideal. I was mainly simply commenting on the fact that it *was* possible.

    Arrays are easy to serialize. Objects...take a bit more code acrobatics: http://php.net/manual/en/language.oo...ialization.php

    I did say "shoehorn", after all.

    A possible example:

    PHP Code:
    define('PERMISSION_ADMIN','Administrator');
    define('PERMISSION_EDITOR','Editor');
    define('PERMISSION_GUEST','Guest');
    define('PERMISSIONS,serialize(array(PERMISSION_ADMIN, PERMISSION_EDITOR, PERMISSION_GUEST)));

    $dataUserPermission='
    Editor'; //from database, $_POST, or wherever.

    if(in_array($dataUserPermission, unserialize(PERMISSIONS)){
        echo '
    is valid';
        if($dataUserPermission==PERMISSION_EDITOR){
              echo '
    is editor';
        }

    Visit The Blog | Follow On Twitter
    301tool 1.1.5 - URL redirector & shortener (PHP/MySQL)
    Can be hosted on and utilize your own domain

  5. #30
    SitePoint Member
    Join Date
    Aug 2013
    Posts
    5
    Mentioned
    0 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by asp_funda View Post
    A programming language is Object Oriented if it satisfies 3 base principles:
    1. Encapsulation
    2. Polymorphism
    3. Inheritance
    I'm new to OOP, can you help me understand what each of those principles are?

    P.S. I looked at the Syntax Hiliter in your sig for WP, did you code that?

  6. #31
    Barefoot on the Moon! silver trophy
    Force Flow's Avatar
    Join Date
    Jul 2003
    Location
    Northeastern USA
    Posts
    4,516
    Mentioned
    51 Post(s)
    Tagged
    1 Thread(s)
    Quote Originally Posted by c.nickerson View Post
    I'm new to OOP, can you help me understand what each of those principles are?
    http://en.wikipedia.org/wiki/Encapsu...programming%29
    http://en.wikipedia.org/wiki/Polymor...ed_programming
    http://en.wikipedia.org/wiki/Inherit...programming%29
    Visit The Blog | Follow On Twitter
    301tool 1.1.5 - URL redirector & shortener (PHP/MySQL)
    Can be hosted on and utilize your own domain

  7. #32
    SitePoint Guru bronze trophy
    Join Date
    Dec 2003
    Location
    Poland
    Posts
    925
    Mentioned
    7 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Hall of Famer View Post
    1. Not everything is an object, string and array for instance.
    I don't think I would want this in PHP considering the fact that objects in PHP result in a pretty performance overhead. Primitive types like strings and arrays are used very often so this could have tangible negative consequences.

    For example, PHP 5 introduced DateTime class with their methods - they are very convenient but when I used them for date and time conversions where I had to create a DateTime object and a DateTimeZone object for each conversion - when I put in a loop it resulted in a huge performance penalty on pages with hundreds of dates. I certainly wouldn't want to deal with such problems while using strings and arrays. Maybe if PHP were a compiled language, then yes.

    PHP must be practical for being used on the web so performance is very important - it's all about compromise.

  8. #33
    SitePoint Addict bronze trophy
    Join Date
    Apr 2013
    Location
    Ithaca
    Posts
    338
    Mentioned
    6 Post(s)
    Tagged
    1 Thread(s)
    Quote Originally Posted by Lemon Juice View Post
    I don't think I would want this in PHP considering the fact that objects in PHP result in a pretty performance overhead. Primitive types like strings and arrays are used very often so this could have tangible negative consequences.

    For example, PHP 5 introduced DateTime class with their methods - they are very convenient but when I used them for date and time conversions where I had to create a DateTime object and a DateTimeZone object for each conversion - when I put in a loop it resulted in a huge performance penalty on pages with hundreds of dates. I certainly wouldn't want to deal with such problems while using strings and arrays. Maybe if PHP were a compiled language, then yes.

    PHP must be practical for being used on the web so performance is very important - it's all about compromise.
    Well you have a point when it comes to certain data types such as primitive numbers and boolean values, but Id still say a good object oriented language needs at least Strings and Arrays to be objects. Every well-known object oriented programming language does it this way, in Java and C# strings and arrays are objects, while in Ruby everything is an object(and for some reason, the overhead issue does not seem to be a big concern). Not sure with Python though, but its also considered a more object oriented language. PHP needs to catch up on this aspect, I like what features they've brought in but its not sufficient yet. On the other hand, I doubt PHP's DateTime class is even fully optimized at this point, which may be part of the cause of your problem?

  9. #34
    SitePoint Guru
    Join Date
    Nov 2003
    Location
    Huntsville AL
    Posts
    663
    Mentioned
    3 Post(s)
    Tagged
    0 Thread(s)
    Well, C++ is the grand daddy of Java/C# and is probably much more widely used then either. However, just like php, C++ lets you use objects for strings and arrays if you want but also supports the primitive types. PHP already has a several array like interfaces so it's easy enough to make objects act like arrays. Defining a master String interface would be nice as well as a reference String implementation that was unicode based.

  10. #35
    Barefoot on the Moon! silver trophy
    Force Flow's Avatar
    Join Date
    Jul 2003
    Location
    Northeastern USA
    Posts
    4,516
    Mentioned
    51 Post(s)
    Tagged
    1 Thread(s)
    Quote Originally Posted by Lemon Juice View Post
    For example, PHP 5 introduced DateTime class with their methods - they are very convenient but when I used them for date and time conversions where I had to create a DateTime object and a DateTimeZone object for each conversion - when I put in a loop it resulted in a huge performance penalty on pages with hundreds of dates.
    The DateTime class has a procedural way of doing things, in addition to the OOP way. I'd be interested to see if there is a performance difference between the two or not.

    See example #1: http://php.net/manual/en/datetime.construct.php
    Also see this date formatting example: http://www.sitepoint.com/forums/show...=1#post5554889

    Quote Originally Posted by ahundiak View Post
    Well, C++ is the grand daddy of Java/C# and is probably much more widely used then either.
    C is the precursor to C++, Java, and C#. C++ didn't directly lead to Java and C#, although all these languages did have a part in influencing each other.

    C++ is one of the top programming languages, but not *the* top. Here are some stats, but take them with a grain of salt: http://www.tiobe.com/index.php/conte...pci/index.html
    Visit The Blog | Follow On Twitter
    301tool 1.1.5 - URL redirector & shortener (PHP/MySQL)
    Can be hosted on and utilize your own domain

  11. #36
    SitePoint Wizard silver trophybronze trophy asp_funda's Avatar
    Join Date
    Jun 2003
    Location
    ether
    Posts
    4,479
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Force Flow View Post
    Ok, in that case:

    PHP Code:
    class thing {
        private 
    $attribute null;

        function 
    __construct($attr){
             
    $this->attribute=$attry;
        }

        function 
    getAttribute(){
             return 
    $this->attribute;
         }
    }

    $newthing = new thing('something');
    echo 
    $newthing->getAttribute(); 
    That essentially allows you to set the variable once, and get it at any time.
    Or you could use __get() magic method do this:

    PHP Code:
    class thing {
        private 
    $attribute;
        private 
    $some_var 'pqr';

        public function 
    __construct($attr) {
             
    $this->attribute $attry;
        }

        public function 
    __get$var_name ) {
             if( isset( 
    $this->$var_name ) ) {
                 return 
    $this->$var_name;
             }
         }
    }

    $newthing = new thing'something' );
    echo 
    $newthing->attribute
    I didn't say its not possible currently, I said it would reduce the extra work of adding getter methods.

    Quote Originally Posted by Force Flow View Post
    You could use serialize/unserialize to shoehorn arrays and objects into a const.
    Yes but that's unnecessary extra work. I'd also like the ability to initialize class constants with value from a function output or for the ability to use final properties.
    Our lives teach us who we are.
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Me - Photo Blog - Personal Blog - Dev Blog
    iG:Syntax Hiliter -- Colourize your code in WordPress!!

  12. #37
    SitePoint Wizard silver trophybronze trophy asp_funda's Avatar
    Join Date
    Jun 2003
    Location
    ether
    Posts
    4,479
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by c.nickerson View Post
    P.S. I looked at the Syntax Hiliter in your sig for WP, did you code that?
    Yup
    Our lives teach us who we are.
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Me - Photo Blog - Personal Blog - Dev Blog
    iG:Syntax Hiliter -- Colourize your code in WordPress!!

  13. #38
    Hosting Team Leader silver trophybronze trophy
    cpradio's Avatar
    Join Date
    Jun 2002
    Location
    Ohio
    Posts
    4,807
    Mentioned
    141 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by asp_funda View Post
    I'd also like the ability to initialize class constants with value from a function output
    Why? Doesn't that defeat the purpose? or at the very least a bit ironic?
    Be sure to congratulate xMog on earning April's Member of the Month
    Go ahead and blame me, I still won't lose any sleep over it
    My Blog | My Technical Notes

  14. #39
    SitePoint Guru bronze trophy
    Join Date
    Dec 2003
    Location
    Poland
    Posts
    925
    Mentioned
    7 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Force Flow View Post
    The DateTime class has a procedural way of doing things, in addition to the OOP way. I'd be interested to see if there is a performance difference between the two or not.
    You can test it easily if you want. In my specific case I needed to do timezone conversion. What I discovered was that simply passing new DateTimeZone() to the DateTime constructor produced noticeable overhead. Sure, using it a few times doesn't make much difference but if I need to do many more conversions in a loop and then it begins to matter. I ended up in constructing DateTimeZone once and caching it in a static variable, which helped a lot in that case.

    If I have to deal with such problems then I would prefer time zone to not be an object in the first place.

    String and array manipulation is a very common task so that's why I wouldn't like them to become slow just for the sake of OO purity. I don't know how other languages manage this problem. If PHP were able to cope with it well then I wouldn't mind.

  15. #40
    SitePoint Addict bronze trophy
    Join Date
    Apr 2013
    Location
    Ithaca
    Posts
    338
    Mentioned
    6 Post(s)
    Tagged
    1 Thread(s)
    From what I see the DateTimeZone class may not be well optimized, it wont surprise me though.

    Quote Originally Posted by Lemon Juice View Post
    String and array manipulation is a very common task so that's why I wouldn't like them to become slow just for the sake of OO purity. I don't know how other languages manage this problem. If PHP were able to cope with it well then I wouldn't mind.
    Yeah, Id definitely be interested in finding out how more complete object oriented languages handle string as object, as they do not turn out to be much slower, maybe not even slightly slower. Apparently there are still ways to optimize classes/objects that PHP needs to explore, after all object instantiation does have overhead but should be negligible compared to the real overheads such as database connection and execution.

  16. #41
    Hosting Team Leader silver trophybronze trophy
    cpradio's Avatar
    Join Date
    Jun 2002
    Location
    Ohio
    Posts
    4,807
    Mentioned
    141 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Lemon Juice View Post
    What I discovered was that simply passing new DateTimeZone() to the DateTime constructor produced noticeable overhead.
    This was in a loop correct? Out of curiosity how often in that loop did each DateTime need a different TimeZone defined? (Just wondering if an optimization could have been reusing the same object instead of defining it new on each iteration -- as I see that in .NET from time to time and it is one of the first changes I'll make)
    Be sure to congratulate xMog on earning April's Member of the Month
    Go ahead and blame me, I still won't lose any sleep over it
    My Blog | My Technical Notes

  17. #42
    SitePoint Guru bronze trophy
    Join Date
    Dec 2003
    Location
    Poland
    Posts
    925
    Mentioned
    7 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by cpradio View Post
    This was in a loop correct? Out of curiosity how often in that loop did each DateTime need a different TimeZone defined? (Just wondering if an optimization could have been reusing the same object instead of defining it new on each iteration -- as I see that in .NET from time to time and it is one of the first changes I'll make)
    Yes, I wrote above that I ended up caching the time zone object in a static variable to optimize this. This was a simple function that converted datetime from one time zone to another so I needed two time zone objects. Of course, in each iteration the needed objects were the same so I could cache them for reuse. I was surprised to see that instantiation of such simple objects of a built-in class could have a noticeable overhead. It was evident that object instantiation was what took most of the resources in the whole process - the very act of converting the date alone was the fastest operation.

    Yes, this was a loop used when displaying comments in a tree view, when there were more than 100 comments I began to notice the overhead of the DateTimeZone object instantiations.

  18. #43
    Hosting Team Leader silver trophybronze trophy
    cpradio's Avatar
    Join Date
    Jun 2002
    Location
    Ohio
    Posts
    4,807
    Mentioned
    141 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Lemon Juice View Post
    Yes, I wrote above that I ended up caching the time zone object in a static variable to optimize this. This was a simple function that converted datetime from one time zone to another so I needed two time zone objects. Of course, in each iteration the needed objects were the same so I could cache them for reuse. I was surprised to see that instantiation of such simple objects of a built-in class could have a noticeable overhead. It was evident that object instantiation was what took most of the resources in the whole process - the very act of converting the date alone was the fastest operation.

    Yes, this was a loop used when displaying comments in a tree view, when there were more than 100 comments I began to notice the overhead of the DateTimeZone object instantiations.
    .NET has the same problem (even with String concatenation, which is why objects like StringBuilder exist) and it is a compiled language. One of the things I learned early on, is to watch your instantiation closely around loops, threaded activities, etc. as performance will begin to show if you don't pay careful attention.

    Just to give an example (a really bad example of the string scenario)
    Code C#:
    string endResult = string.Empty;
    for (int i = 0; i < 100000; i++)
        endResult += string.Format("Item {0}", i.ToString());

    StringBuilder on the other hand optimizes a lot of components when needing to work with a large string or a lot of concatenations
    Code C#:
    StringBuilder endResult = new StringBuilder(500000); // set aside the length you think you may need
    for (int i =0; i < 100000; i++)
        endResult.AppendFormat("Item {0}", i.ToString());

    Likewise, I've seen very similar issues with the DateTime object in .NET that you described with PHP. The issue you encounter is the memory allocation. Each use of new X is going to place a X into a new memory location. Throw that into a loop and you'll quickly see why that degrades performance. Any time X is reusable, it should be reused, or another way to clean it up, destroy X once you are done with it (might not see all the performance you could gain until garbage collection occurs).
    Be sure to congratulate xMog on earning April's Member of the Month
    Go ahead and blame me, I still won't lose any sleep over it
    My Blog | My Technical Notes

  19. #44
    SitePoint Guru bronze trophy
    Join Date
    Dec 2003
    Location
    Poland
    Posts
    925
    Mentioned
    7 Post(s)
    Tagged
    0 Thread(s)
    Thanks, it's interesting to know the problem exists in other languages as well. However, I'm not fully convinced that memory allocation is the cause of the overhead. When I construct a new string or array in PHP they also need memory allocation but this process is very fast. Sure, if an object is large then a lot of memory must be allocated but to me it looks like there must something more intensive going on when a new object is instantiated. If this problem is in other languages then perhaps it's the nature of the beast and it's hard to do any optimizations here.

  20. #45
    SitePoint Wizard silver trophybronze trophy Stormrider's Avatar
    Join Date
    Sep 2006
    Location
    Nottingham, UK
    Posts
    3,133
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)
    It's silly to say the implementation of OO in any particular language is 'complete' or not - as long as it satisfies the base principles outlined above (which PHP does). It may have more or less features than another language, but the languages are constantly evolving so just because (say) Java adds some OO feature/trick, doesn't suddenly make all other languages which don't implement this 'incomplete' in some way. So yes, PHP's OOP implementation is 'complete', even though it doesn't have everything that other languages do.

  21. #46
    SitePoint Wizard silver trophybronze trophy asp_funda's Avatar
    Join Date
    Jun 2003
    Location
    ether
    Posts
    4,479
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by cpradio View Post
    Why? Doesn't that defeat the purpose? or at the very least a bit ironic?
    Yes, constants are not supposed to do that but PHP doesn't allow final properties either, so either this or final properties should be implemented.
    Our lives teach us who we are.
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Me - Photo Blog - Personal Blog - Dev Blog
    iG:Syntax Hiliter -- Colourize your code in WordPress!!

  22. #47
    Hosting Team Leader silver trophybronze trophy
    cpradio's Avatar
    Join Date
    Jun 2002
    Location
    Ohio
    Posts
    4,807
    Mentioned
    141 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Lemon Juice View Post
    Thanks, it's interesting to know the problem exists in other languages as well. However, I'm not fully convinced that memory allocation is the cause of the overhead. When I construct a new string or array in PHP they also need memory allocation but this process is very fast. Sure, if an object is large then a lot of memory must be allocated but to me it looks like there must something more intensive going on when a new object is instantiated. If this problem is in other languages then perhaps it's the nature of the beast and it's hard to do any optimizations here.
    Yeah, I'm sure there is more to it, but I know the last time I ran a performance monitor on similar code, the memory usage shot up like crazy (in .NET), I think it was due to the way objects are stored on the heap and persisted across garbage collection (and whether it falls into tier 1, 2, 3 or 4 of garbage collection). Maybe there is something else that happens underneath too, but it definitely happens in .NET and you've found it in PHP, so they both likely do some implementation very similar to see that happen in both languages.

    Quote Originally Posted by Stormrider View Post
    It's silly to say the implementation of OO in any particular language is 'complete' or not - as long as it satisfies the base principles outlined above (which PHP does). It may have more or less features than another language, but the languages are constantly evolving so just because (say) Java adds some OO feature/trick, doesn't suddenly make all other languages which don't implement this 'incomplete' in some way. So yes, PHP's OOP implementation is 'complete', even though it doesn't have everything that other languages do.
    That would be my fault of choosing a poor title, since I split the thread from another discussion, as this one blossomed into all sorts of directions around PHP's OOP implementation.

    Quote Originally Posted by asp_funda View Post
    Yes, constants are not supposed to do that but PHP doesn't allow final properties either, so either this or final properties should be implemented.
    Gotcha. I do miss not being able to use readonly, final, and other attributes/properties too. Surprisingly, I must not do as much heavy programming in PHP as I don't seem to run into "Man, I wish I had this or that" a lot while in PHP. It does happen occasionally, just not as often as I would have thought.
    Be sure to congratulate xMog on earning April's Member of the Month
    Go ahead and blame me, I still won't lose any sleep over it
    My Blog | My Technical Notes

  23. #48
    SitePoint Wizard silver trophybronze trophy asp_funda's Avatar
    Join Date
    Jun 2003
    Location
    ether
    Posts
    4,479
    Mentioned
    1 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by cpradio View Post
    Surprisingly, I must not do as much heavy programming in PHP as I don't seem to run into "Man, I wish I had this or that" a lot while in PHP. It does happen occasionally, just not as often as I would have thought.
    Sometimes I feel it when I recall the time long ago I used to work in Java but I guess not missing these things often is more related to being used to PHP not having them and working around them.
    Our lives teach us who we are.
    ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Me - Photo Blog - Personal Blog - Dev Blog
    iG:Syntax Hiliter -- Colourize your code in WordPress!!

  24. #49
    SitePoint Guru
    Join Date
    Nov 2003
    Location
    Huntsville AL
    Posts
    663
    Mentioned
    3 Post(s)
    Tagged
    0 Thread(s)
    Quote Originally Posted by Force Flow View Post
    C is the precursor to C++, Java, and C#. C++ didn't directly lead to Java and C#, although all these languages did have a part in influencing each other.
    Agreed. Predecessor/precursor are much better terms than grandfather.

  25. #50
    SitePoint Addict bronze trophy
    Join Date
    Apr 2013
    Location
    Ithaca
    Posts
    338
    Mentioned
    6 Post(s)
    Tagged
    1 Thread(s)
    Just found out that PHP 5.4's Closure class can achieve Metaprogramming in an alternative way:
    http://www.php.net/manual/en/closure.bind.php

    Although it's not as elegant as runkit when it comes down to Metaprogramming, it seems to be working at least and does not require installation from PECL. Still, the fact that it's not compatible with PHP 5.3 means that it cannot be used in plugin developments for internet applications as most webhosts still do not offer PHP 5.4. Doubt this will happen soon though, will likely have to wait another 2-3 years.


Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •