Deleting a preloaded image from memory

Discussion in 'Javascript' started by ivan.leben@gmail.com, May 17, 2006.

  1. Guest

    How can I really delete a preloaded image from memory/disk cache? Let's
    say I preload an image by creating an Image object and setting its src
    attribute to desired URL:

    var img = new Image();
    img.src = [someurl];

    Then I use the image a few more times by adding it into an Array
    object:

    var images = new Array();
    images.push(img);

    I found out that just calling 'delete' on a pointer to that Image
    object, doesn't free up the RAM.

    delete images[0]; //RAM is not freed here!

    Should I call delete on all the references to the image object? This
    would be a real pain, since I have to check about 3000 lines of code
    for possible references to it and make sure I 'delete' all of them...
    What about the other new Image objects, that get their src attribute
    set to the same url?
    , May 17, 2006
    #1
    1. Advertising

  2. wrote:

    > How can I really delete a preloaded image from memory/disk cache? Let's
    > say I preload an image by creating an Image object and setting its src
    > attribute to desired URL:
    >
    > var img = new Image();
    > img.src = [someurl];


    img = null;

    > Then I use the image a few more times by adding it into an Array
    > object:
    >
    > var images = new Array();
    > images.push(img);
    >
    > I found out that just calling 'delete' on a pointer to that Image
    > object, doesn't free up the RAM.
    >
    > delete images[0]; //RAM is not freed here!


    images = null;

    > [...]


    Hope this helps,

    --
    Bart
    Bart Van der Donck, May 17, 2006
    #2
    1. Advertising

  3. Guest

    Setting a pointer to null obviously won't delete the object pointed to
    from memory, but just change the address the pointer is referencing
    (from address of the object to null = 0x0000000). The object might get
    deleted if the memory is managed and a garbage collector finds out
    there is no more reference to the object in question. However if any
    other pointer is still referencing the same object, the memory manager
    will keep it in memory. That's just how it works.

    The solution you gave me is not just useless, but even less effective
    than the one I wrote in the question myself. Any other ideas?
    , May 17, 2006
    #3
  4. wrote:

    > Setting a pointer to null obviously won't delete the object pointed to
    > from memory, but just change the address the pointer is referencing
    > (from address of the object to null = 0x0000000). The object might get
    > deleted if the memory is managed and a garbage collector finds out
    > there is no more reference to the object in question. However if any
    > other pointer is still referencing the same object, the memory manager
    > will keep it in memory.


    I've done some investigation about this issue. My way (setting to
    'null') and your way (delete method) do not seem to free up any memory
    of the objects (CPU benchmarks on MSIE and FF). My conclusion is that
    there is no reliable way to do what you want. There's only one JScript
    function:

    CollectGarbage();

    But that is (explicitly) undocumented and (explicitly) unofficial
    though, and that usually has a good reason.

    Some good references and quotes:

    http://groups.google.com/group/comp.lang.javascript/browse_frm/thread/1d97e35c3a102831/:

    "The problem is that you don't really have a way to know when the
    garbage collector will free the memory. It is a task with low priority"

    http://msdn.microsoft.com/msdnmag/issues/03/09/WebQA/default.aspx:

    "Now, you can force the JScript garbage collector to run with the
    CollectGarbage() method, but I don't recommend it. The whole point of
    JScript having a GC is that you don't need to worry about object
    lifetime. If you do worry about it then you're probably using the wrong
    tool for the job!"

    http://msdn.microsoft.com/msdnmag/issues/03/09/WebQA/default.aspx:

    "JScript was designed to provide a quick, easy way to write simple
    scripts on Web pages. The fact that you're asking at all makes me think
    that you're using the wrong tool for the job."

    http://groups.google.com/group/micr....jscript/browse_frm/thread/208e811edbedf33d/:

    "Yes, calling CollectGarbage() is wrong. It's undocumented for a
    reason. It won't solve any of your problems."

    --
    Bart
    Bart Van der Donck, May 17, 2006
    #4
  5. Guest

    Yes, garbage collector is a low-priority task that should run
    automatically in JavaScript, just as it does in Java, C# and other
    'modern' languages. Its designed to 'ease' the memory handling. But the
    more I think about my problem, the more I get the sense that it's
    probably not really connected to garbage collector.

    I think objects that get cached by a browser are handled on
    another/higher level, than other "programmatical" objects, created by a
    script. In fact we are speaking about two different kinds of memory
    data - one is the data that is put in cache (image bytes, html text)
    and the other is data of DOM programming objects (which make a language
    'object oriented').

    The programming objects are handled by a 'garbage collector' and are
    freed after no pointer references them anymore. On the other side, the
    cached data can still be left there (in cache) even after one closes
    the browser application (that means in the 'disk cache' memory) in
    order to make the rendering of the page faster next time in a short
    period. The pure proof of this is that even when i close the browser
    (and I see that RAM gets freed), the next time I open it and run the
    same web application preloading the same images, they get 'loaded' in
    an instance.

    There should be (if they exist at all) some other functions not related
    to garbage collector to manage the data that is cached. I know how to
    explicitly make a page not being cached, by adding some special tags
    into the html file. However this is not my preference, because I want
    to be able to preload images when I need to, so I wonder: is there any
    way to control (delete) the cached data once its cached?
    , May 17, 2006
    #5
  6. Guest

    To clarify my problem I will give an example of what I'm really trying
    to achieve:

    My application preloads images one after another when the user browses
    a gallery, so there are always 10 images loaded in advance. These
    images get shown immediately when the user reaches them, so she doesn't
    have to wait.

    Now when the user had already browsed over 100 of images, I would like
    to delete some of them at the beginning of the 'playlist' and free the
    memory so my application can run this way for hours.

    How do I achieve this?
    , May 17, 2006
    #6
  7. wrote:

    > To clarify my problem I will give an example of what I'm really trying
    > to achieve:
    >
    > My application preloads images one after another when the user browses
    > a gallery, so there are always 10 images loaded in advance. These
    > images get shown immediately when the user reaches them, so she doesn't
    > have to wait.


    I think you're looking for a functionality like SQL's FLUSH or Perl's
    buffer disable/clean on command. I don't believe this can be controlled
    on-the-fly in browsers, though there are META-instructions to control
    this on page-level:

    <META HTTP-EQUIV="cache-control" CONTENT="no-cache">
    <META HTTP-EQUIV="expires" CONTENT="Thu, 8 May 2006 11:30:00 GMT">
    (or whatever date)
    <META HTTP-EQUIV="pragma" CONTENT="no-cache">

    > Now when the user had already browsed over 100 of images, I would like
    > to delete some of them at the beginning of the 'playlist' and free the
    > memory so my application can run this way for hours.
    > How do I achieve this?


    The whole idea is that a browser should do all this for you, so you
    don't have to worry about it (ideally). I would advocate the use of
    another computer language if you need this kind of low level memory
    block access.

    You could develop the gallery in Macromedia Flash, end let the SWF-file
    handle its own memory objects (I believe this would stand apart from
    the browser's memory allocation). I'm not sure if Flash/ActionScript
    could go as low as influencing RAM on-the-fly. Maybe some Flash
    Newsgroup could shed a light on this.

    --
    Bart
    Bart Van der Donck, May 18, 2006
    #7
  8. Guest

    The problem is I really need to achieve this in Firefox because I am
    making an extension.
    , May 19, 2006
    #8
  9. wrote:

    > Setting a pointer to null obviously won't delete the object pointed to
    > from memory,


    True, except of the "pointer" term. This is ECMAScript, not C; there are
    references, not pointers.

    The operation marks the object referred to for garbage collection, unless
    there are other references to that object.

    > but just change the address the pointer is referencing
    > (from address of the object to null = 0x0000000).


    Pure speculation.


    PointedEars
    --
    Indiana Jones: The Name of God. Jehovah.
    Professor Henry Jones: But in the Latin alphabet,
    "Jehovah" begins with an "I".
    Indiana Jones: J-...
    Thomas 'PointedEars' Lahn, May 23, 2006
    #9
  10. wrote:

    > The problem is I really need to achieve this in Firefox because I am
    > making an extension.


    There is no need for preloading in the first place.


    PointedEars
    Thomas 'PointedEars' Lahn, May 23, 2006
    #10
  11. Thomas 'PointedEars' Lahn wrote:

    > wrote:
    >
    > > The problem is I really need to achieve this in Firefox because I am
    > > making an extension.

    >
    > There is no need for preloading in the first place.


    I'm thinking in the same direction, yes.

    To the original poster:
    In stead of shoe-horning your way through browsers' internal memory
    block allocation, why not use plain simple HTML code. It works for
    everybody else's image galleries, so why not for you ? Sure, one could
    say something for your preloading idea. The obvious benefit is that a
    surfer doesn't need to wait for the new images. But the same actually
    applies to any web page. Say you have a homepage with a language choice
    English/Dutch, why wouldn't you already preload the next 2 pages ?

    I think your scenario has more disadvantages than benefits. I'ld
    counsel a plain HTML strategy if I were you.

    --
    Bart
    Bart Van der Donck, May 23, 2006
    #11
  12. Bart Van der Donck wrote:

    > Thomas 'PointedEars' Lahn wrote:
    >> wrote:
    >> > The problem is I really need to achieve this in Firefox because I am

    ^^^^^^^
    >> > making an extension.

    ^^^^^^^^^
    >> There is no need for preloading in the first place.

    >
    > I'm thinking in the same direction, yes.
    >
    > To the original poster:
    > In stead of shoe-horning your way through browsers' internal memory
    > block allocation, why not use plain simple HTML code. It works for
    > everybody else's image galleries, so why not for you ? Sure, one could
    > say something for your preloading idea. The obvious benefit is that a
    > surfer doesn't need to wait for the new images. But the same actually
    > applies to any web page. Say you have a homepage with a language choice
    > English/Dutch, why wouldn't you already preload the next 2 pages ?
    >
    > I think your scenario has more disadvantages than benefits. I'ld
    > counsel a plain HTML strategy if I were you.


    Full ACK for (X)HTML. The `link' element can facilitate preloading if
    it is considered really necessary.

    But: Am I missing something here, or wasn't a Firefox extension running
    on the Gecko chrome, hence on _XUL_? I fail to find /any/ need for
    preloading _local_ resources; computers are this fast. IMHO, preloading
    is only for resources retrieved from the server, for later local use.
    Especially, probably XUL has the means so that no Image object needs to
    be used, that memory is freed when the object is no longer used and that
    switching images works smoothly anyway.


    PointedEars
    --
    Homer: I have changed the world. Now I know how it feels to be God!
    Marge: Do you want turkey sausage or ham?
    Homer: Thou shalt send me *two*, one of each kind.
    (Santa's Little Helper [dog] and Snowball [cat] run away :))
    Thomas 'PointedEars' Lahn, May 23, 2006
    #12
  13. wrote:

    > How can I really delete a preloaded image from memory/disk cache?


    You can _not_. You cannot even be sure that an image resource was cached.

    And why would you want to do that anyway? The cache is not your business.
    If the resource in the cache is outdated, use cache control headers to tell
    the UA that this is the case. If it is not outdated, then why delete it?
    Maybe you are confusing cache (file resource) and heap (memory resource).
    Script objects are stored on the heap, not in the cache. Deleting an
    object on the cache does not free heap memory and vice-versa.

    > [...]
    > delete images[0]; //RAM is not freed here!


    Then there is probably another reference to that object. But, how are you
    trying to determine "RAM" usage?

    > Should I call delete on all the references to the image object?


    No, you only need to `delete' those that are not defined local.
    (You have to cared about scoping before? Tough luck.)

    > What about the other new Image objects, that get their src attribute
    > set to the same url?


    The `src' _property_ does not matter here.

    var img1 = new Image(); img1.src = "foo";

    and

    var img2 = new Image(); img2.src = "foo";

    are still two different Image objects that require memory each. They maybe
    use the same cached resource, that is all. That said, using different
    Image objects for the same image resource is simply BAD -- Broken As
    Designed.


    PointedEars
    --
    When you have eliminated all which is impossible, then
    whatever remains, however improbable, must be the truth.
    -- Sherlock Holmes in Sir Arthur Conan Doyle's
    "The Blanched Soldier"
    Thomas 'PointedEars' Lahn, May 23, 2006
    #13
  14. Thomas 'PointedEars' Lahn wrote:

    > wrote:
    > > but just change the address the pointer is referencing
    > > (from address of the object to null = 0x0000000).

    >
    > Pure speculation.


    That is no speculation - it's just how this works. The 0x0(0)(0)...
    address is the null pointer by default. Its notation (e.g. 0x0000000)
    just depends on 8, 16, 32, etc bit memory, but it always refers to null
    as the "very first" pre-reserved memory address.

    Setting a javascript variable to null is just re-referencing it from
    its current block to the one that belongs to null. The browsers that I
    tested do not compile this action with a pragma to empty the referenced
    memory though (supposed the address is not used anywhere else anymore).

    Yes, I was surprised about the results of my ealier CPU benchmarks in
    MSIE&FF. I expected the memory addresses would be cleaned up quite fast
    if there were no references to it anymore (even with low job priority).

    --
    Bart
    Bart Van der Donck, May 24, 2006
    #14
  15. Bart Van der Donck wrote:
    > Thomas 'PointedEars' Lahn wrote:
    >> wrote:
    >>> but just change the address the pointer is referencing
    >>> (from address of the object to null = 0x0000000).

    >>
    >> Pure speculation.

    >
    > That is no speculation - it's just how this works. The 0x0(0)(0)...
    > address is the null pointer by default. Its notation (e.g. 0x0000000)
    > just depends on 8, 16, 32, etc bit memory, but it always refers to
    > null as the "very first" pre-reserved memory address.
    >
    > Setting a javascript variable to null is just re-referencing it from
    > its current block to the one that belongs to null. ...

    <snip>

    You appear to be confusing javascript with C or some other language.
    Javascript has no 'pointer' data types, its Null value is a primitive
    type (so does not even have to be a reference of any sort, just an
    arbitrary internal value) and the mechanism employed internally is not
    specified in the applicable language specification and almost certainly
    is not consistent across implementations.

    You are speculating, and even reading some open source implementations
    and making statements about what they do is irrelevant to the issues of
    javascript authoring as those observations could never be applied to
    all language implementations.

    Richard.
    Richard Cornford, May 24, 2006
    #15
  16. Thomas 'PointedEars' Lahn wrote:

    > wrote:
    > > [...]
    > > delete images[0]; //RAM is not freed here!

    >
    > Then there is probably another reference to that object.


    The whole point of this discussion is that the object is fully
    dereferenced, but the address itself still remains available internally
    as a memory block.

    > But, how are you trying to determine "RAM" usage?


    On WinXP: CTRL-ALT-Delete > tab 'Processes' > 'Memory use'. On Unix,
    see the 'top' command.

    > > Should I call delete on all the references to the image object?

    >
    > No, you only need to `delete' those that are not defined local.
    > (You have to cared about scoping before? Tough luck.)


    There is a chance scoping could help, but frankly I don't think so
    (haven't tested).

    --
    Bart
    Bart Van der Donck, May 24, 2006
    #16
  17. Richard Cornford wrote:

    > [...]
    > You appear to be confusing javascript with C or some other language.


    I'm not talking about javascript code. I'm talking about how a browser
    compiles javascript code.

    > Javascript has no 'pointer' data types


    Indeed, not at the high javascript code level - but it does at the
    browser's low compile level. These are just general basic computer
    mechanisms. Every variable points (or 'references' if you like) to a
    memory block address. That isn't visible at the surface in javascript,
    but is definitely how it works internally. Referencing and memory
    allocation take place when the browser compiles the javascript to
    something the machine understands. That's why it's so difficult to
    influence memory handling from within javascript.

    > its Null value is a primitive


    No, 'null' is a well defined address (must be) and its reference is
    somewhere between 0x000 and 0x0000000000000 (BTW, null is not a value,
    it's the "not-value" that is defined that way by 0x0...).

    > type (so does not even have to be a reference of any sort, just an
    > arbitrary internal value) and the mechanism employed internally is not
    > specified in the applicable language specification and almost certainly
    > is not consistent across implementations.


    Any computer language works with memory allocation/release and
    (de)referencing to those.

    > You are speculating,


    No, I am not

    > and even reading some open source implementations
    > and making statements about what they do is irrelevant to the issues of
    > javascript authoring as those observations could never be applied to
    > all language implementations.


    You're right - this discussion is irrelevant to javascript authoring
    itself.

    --
    Bart
    Bart Van der Donck, May 24, 2006
    #17
  18. Bart Van der Donck wrote:
    > Richard Cornford wrote:
    >
    > > [...]
    > > You appear to be confusing javascript with C or some other language.

    >
    > I'm not talking about javascript code. I'm talking about how
    > a browser compiles javascript code.


    Browsers are not the only software that executes javascript code, and
    you don't know how it is done in 'a browser', or anywhere else, in
    general. You can only examine how it is done in specific
    implementations, and cannot validly generalise beyond that. When you
    are thinking about this remember that there is at least one javascript
    implementation written in javascript.

    >> Javascript has no 'pointer' data types

    >
    > Indeed, not at the high javascript code level - but it does at the
    > browser's low compile level.


    Not necessarily. IceBrowser uses Rhino for its javascript engine, and
    Rhino is written in Java, so has no pointers. If you insist on going
    down through the layers you will end up at the machine code level,
    where there are no 'pointers', only integers loaded into data and
    address registers, etc.

    > These are just general basic computer
    > mechanisms. Every variable points (or 'references' if you like) to a
    > memory block address.


    A memory address, it is only conceptually a block when some (byte)
    length information is also associated with the value.

    > That isn't visible at the surface in javascript,
    > but is definitely how it works internally.


    Which may be no more useful a statement than observing that CPUs
    execute machine code.

    > Referencing and memory allocation take place when the
    > browser compiles the javascript to
    > something the machine understands.


    Rhino does not compile javascript to something the machine understands,
    it compiles it to something the JVM understands, and the JVM does the
    next step.

    > That's why it's so difficult to
    > influence memory handling from within javascript.


    The difficulty is because javascript uses automatic garbage collection,
    which is not intended to be influenced by executing code.

    >> its Null value is a primitive

    >
    > No, 'null' is a well defined address (must be)


    No, in javascript Null (the value that is assigned with - x = null -)
    is a primitive value, and may or may not have any association with a
    memory address.

    > and its reference is
    > somewhere between 0x000 and 0x0000000000000


    An address between zero and zero (not a very wide gap)?

    > (BTW, null is not a value,
    > it's the "not-value" that is defined that way by 0x0...).


    Not in javascript. In javascript Null is a primitive type with a single
    value. The nature of that value is not specified or important. It may
    be entirely arbitrary, or borrowed from the implementation language.

    >> type (so does not even have to be a reference of any sort, just an
    >> arbitrary internal value) and the mechanism employed internally is not
    >> specified in the applicable language specification and almost certainly
    >> is not consistent across implementations.

    >
    > Any computer language works with memory allocation/release
    > and (de)referencing to those.


    Memory allocation is not part of machine code. The lowest level at
    which memory allocation would be expected is at the level of the OS.
    And once you get far enough up that the memory allocation has been
    abstracted outside of your control it stops being part of the picture
    again.

    >> You are speculating,

    >
    > No, I am not


    Oh yes you are. You just don't have access to the information necessary
    to make these generalisations.

    >> and even reading some open source implementations and
    >> making statements about what they do is irrelevant to the issues of
    >> javascript authoring as those observations could never be applied to
    >> all language implementations.

    >
    > You're right - this discussion is irrelevant to javascript authoring
    > itself.


    So irrelevant to this group.

    Richard.
    Richard Cornford, May 24, 2006
    #18
  19. Bart Van der Donck wrote:

    > Thomas 'PointedEars' Lahn wrote:
    >> wrote:
    >> > [...]
    >> > delete images[0]; //RAM is not freed here!

    >>
    >> Then there is probably another reference to that object.

    >
    > The whole point of this discussion is that the object is fully
    > dereferenced, but the address itself still remains available
    > internally as a memory block.


    The OP did write about other references to that object, see the citation
    below.

    BTW: You should look up the meaning of "(to) dereference".

    >> But, how are you trying to determine "RAM" usage?

    >
    > On WinXP: CTRL-ALT-Delete > tab 'Processes' > 'Memory use'. On Unix,
    > see the 'top' command.


    Don't patronize me. That question was intentionally directed to the OP.

    And the programs you mentioned (that I was well aware of) display only
    memory usage of the _browser process_. Especially for Firefox, this does
    not bear any meaning regarding memory usage of the script engine and
    memory allocated for script objects, due to its known memory leaks.

    >> > Should I call delete on all the references to the image object?

    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
    >> No, you only need to `delete' those that are not defined local.
    >> (You have to cared about scoping before? Tough luck.)

    >
    > There is a chance scoping could help, but frankly I don't think so
    > (haven't tested).


    Again you have no proof (not even the slightest hint in form of a test
    result) for your wild assumptions at all but you insist on them. Although
    regarding this question, it is very clear from the language specification
    that a locally defined object reference ceases to exist once the execution
    context is left (unless it is part of a closure). However, no more
    references to an object means that the object is marked for garbage
    collection. And the SpiderMonkey engine used by Firefox does not have
    IE's "circular reference" problem.


    PointedEars
    --
    This above all: To thine own self be true.
    -- William Shakespeare (1564-1616)
    Thomas 'PointedEars' Lahn, May 24, 2006
    #19
  20. Richard Cornford wrote:

    > [...]
    > >> You are speculating,

    > >
    > > No, I am not

    >
    > Oh yes you are. You just don't have access to the information necessary
    > to make these generalisations.


    Maybe this will convince you. Say the following javascript code:

    var aVar;

    That was the declaration. The computer reserves a name 'aVar' for
    future use, but this name does not refer to a memory address yet at
    this point.

    aVar = 5;

    That was the assignment. 5 is converted (to keep things simple) to
    binary numerical data (the notation with 1's and 0's). Suppose each
    memory block consists of 8 bits, then the value would become 00000101
    in this case. Then 00000101 is allocated to an address, let's say we
    name the address ABC. A programmer actually instructs the ABC-address
    to remember the value 00000101 for him, in case he would need it later.
    This memory allocation is a physical (electronical/magnetic) thing
    inside the hardware of your PC.

    The variable aVar then gets assigned to memory address ABC. If we
    dereference aVar, we don't need name ABC anymore and we could free that
    address (that is, if it was not used by something else anymore), and
    thus gaining memory space to create new addresses.

    In old computer languages like Assembler, this whole process would need
    to be done manually. Each memory address was a series of (physical)
    bulbs in a computer room. Each byte (corresponding to 8 bits in my
    example) went on and off depending on the value it stored at that
    moment. 1 is on and 0 is off - which is basically still the only thing
    a computer knows (boolean values). I guess that's why early computers
    were always associated by flikkering lamps.

    Since a few decades, the jobs of the flikkering lamps were taken over
    by minimal chipsets in stead of bulbs, today they're even 0,001
    millimeter chips or so in stead of 1 meter of bulbs. Thus the term
    micro-computing and even the company MicroSoft (=software for computers
    with micro-chips).

    --
    Bart
    Bart Van der Donck, May 24, 2006
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Homa
    Replies:
    2
    Views:
    522
    Jerry III
    Oct 21, 2003
  2. Harry Barker
    Replies:
    2
    Views:
    513
    Alf P. Steinbach
    Apr 19, 2006
  3. Replies:
    1
    Views:
    85
    Randy Webb
    Nov 25, 2006
  4. Replies:
    3
    Views:
    141
  5. crea
    Replies:
    2
    Views:
    407
    Nobody
    Dec 28, 2012
Loading...

Share This Page