Adding values to a hash within/over multiple each loops











up vote
0
down vote

favorite












I have a concept called snapshot which basically stores a snapshot of how data looked at a certain period of time. What I'm building is a method that loops through the snapshots for each events, and builds a small hash outlining the ownership over time for a given shareholder.



  def fetch_ownership_over_time(shareholder, captable)

@shareholder = Shareholder.find(shareholder.id)
@captable = Captable.find(captable.id)
@company = @captable.company.id
@ownership_over_time =

@captable.events.collect(&:snapshot).each do |snapshot|
parsed_snapshot = JSON.parse(snapshot)

@ownership_over_time.push(parsed_snapshot["event"]["name"])
@ownership_over_time.push(parsed_snapshot["event"]["date"])

parsed_snapshot["shareholders"].each do |shareholder|
if shareholder["id"] == @shareholder.id

@ownership_over_time.push(shareholder["ownership_percentage"])

end
end
end
return @ownership_over_time
end


I then call this method in my view which successfully retrieves the correct values however they are not structured in any way:



["Event 1 ", "2018-11-19", "0.666666666666667", "Event 2 ", "2018-11-19", "0.333333333333333", "4th event ", "2018-11-19", "0.315789473684211"]


What I'd like to do now though is construct my hash so that each separate snapshot event contains a name, date and ownership_percentage.



Perhaps something like this:



ownership_over_time = [
{
event_name = "Event 1" #parsed_snapshot["event"]["name"]
event_date = "20180202" #parsed_snapshot["event"]["date"]
ownership_percentage = 0.37 #shareholder["ownership_percentage"]
},
{
event_name = "Event 2" #parsed_snapshot["event"]["name"]
event_date = "20180501" #parsed_snapshot["event"]["date"]
ownership_percentage = 0.60 #shareholder["ownership_percentage"]
}
]


My challenge though is that the ["event"]["name"] an ["event"]["date"] attributes I need to fetch when looping over my snapshots i.e. the first loop (.each do |snapshot|) whereas I get my ownership_percentage when looping over shareholders - the second loop (.each do |shareholder|).



So my question is - how can I build this hash in "two" places so I can return the hash with the 3 attributes?



Appreciative of guidance/help - thank you!










share|improve this question




























    up vote
    0
    down vote

    favorite












    I have a concept called snapshot which basically stores a snapshot of how data looked at a certain period of time. What I'm building is a method that loops through the snapshots for each events, and builds a small hash outlining the ownership over time for a given shareholder.



      def fetch_ownership_over_time(shareholder, captable)

    @shareholder = Shareholder.find(shareholder.id)
    @captable = Captable.find(captable.id)
    @company = @captable.company.id
    @ownership_over_time =

    @captable.events.collect(&:snapshot).each do |snapshot|
    parsed_snapshot = JSON.parse(snapshot)

    @ownership_over_time.push(parsed_snapshot["event"]["name"])
    @ownership_over_time.push(parsed_snapshot["event"]["date"])

    parsed_snapshot["shareholders"].each do |shareholder|
    if shareholder["id"] == @shareholder.id

    @ownership_over_time.push(shareholder["ownership_percentage"])

    end
    end
    end
    return @ownership_over_time
    end


    I then call this method in my view which successfully retrieves the correct values however they are not structured in any way:



    ["Event 1 ", "2018-11-19", "0.666666666666667", "Event 2 ", "2018-11-19", "0.333333333333333", "4th event ", "2018-11-19", "0.315789473684211"]


    What I'd like to do now though is construct my hash so that each separate snapshot event contains a name, date and ownership_percentage.



    Perhaps something like this:



    ownership_over_time = [
    {
    event_name = "Event 1" #parsed_snapshot["event"]["name"]
    event_date = "20180202" #parsed_snapshot["event"]["date"]
    ownership_percentage = 0.37 #shareholder["ownership_percentage"]
    },
    {
    event_name = "Event 2" #parsed_snapshot["event"]["name"]
    event_date = "20180501" #parsed_snapshot["event"]["date"]
    ownership_percentage = 0.60 #shareholder["ownership_percentage"]
    }
    ]


    My challenge though is that the ["event"]["name"] an ["event"]["date"] attributes I need to fetch when looping over my snapshots i.e. the first loop (.each do |snapshot|) whereas I get my ownership_percentage when looping over shareholders - the second loop (.each do |shareholder|).



    So my question is - how can I build this hash in "two" places so I can return the hash with the 3 attributes?



    Appreciative of guidance/help - thank you!










    share|improve this question


























      up vote
      0
      down vote

      favorite









      up vote
      0
      down vote

      favorite











      I have a concept called snapshot which basically stores a snapshot of how data looked at a certain period of time. What I'm building is a method that loops through the snapshots for each events, and builds a small hash outlining the ownership over time for a given shareholder.



        def fetch_ownership_over_time(shareholder, captable)

      @shareholder = Shareholder.find(shareholder.id)
      @captable = Captable.find(captable.id)
      @company = @captable.company.id
      @ownership_over_time =

      @captable.events.collect(&:snapshot).each do |snapshot|
      parsed_snapshot = JSON.parse(snapshot)

      @ownership_over_time.push(parsed_snapshot["event"]["name"])
      @ownership_over_time.push(parsed_snapshot["event"]["date"])

      parsed_snapshot["shareholders"].each do |shareholder|
      if shareholder["id"] == @shareholder.id

      @ownership_over_time.push(shareholder["ownership_percentage"])

      end
      end
      end
      return @ownership_over_time
      end


      I then call this method in my view which successfully retrieves the correct values however they are not structured in any way:



      ["Event 1 ", "2018-11-19", "0.666666666666667", "Event 2 ", "2018-11-19", "0.333333333333333", "4th event ", "2018-11-19", "0.315789473684211"]


      What I'd like to do now though is construct my hash so that each separate snapshot event contains a name, date and ownership_percentage.



      Perhaps something like this:



      ownership_over_time = [
      {
      event_name = "Event 1" #parsed_snapshot["event"]["name"]
      event_date = "20180202" #parsed_snapshot["event"]["date"]
      ownership_percentage = 0.37 #shareholder["ownership_percentage"]
      },
      {
      event_name = "Event 2" #parsed_snapshot["event"]["name"]
      event_date = "20180501" #parsed_snapshot["event"]["date"]
      ownership_percentage = 0.60 #shareholder["ownership_percentage"]
      }
      ]


      My challenge though is that the ["event"]["name"] an ["event"]["date"] attributes I need to fetch when looping over my snapshots i.e. the first loop (.each do |snapshot|) whereas I get my ownership_percentage when looping over shareholders - the second loop (.each do |shareholder|).



      So my question is - how can I build this hash in "two" places so I can return the hash with the 3 attributes?



      Appreciative of guidance/help - thank you!










      share|improve this question















      I have a concept called snapshot which basically stores a snapshot of how data looked at a certain period of time. What I'm building is a method that loops through the snapshots for each events, and builds a small hash outlining the ownership over time for a given shareholder.



        def fetch_ownership_over_time(shareholder, captable)

      @shareholder = Shareholder.find(shareholder.id)
      @captable = Captable.find(captable.id)
      @company = @captable.company.id
      @ownership_over_time =

      @captable.events.collect(&:snapshot).each do |snapshot|
      parsed_snapshot = JSON.parse(snapshot)

      @ownership_over_time.push(parsed_snapshot["event"]["name"])
      @ownership_over_time.push(parsed_snapshot["event"]["date"])

      parsed_snapshot["shareholders"].each do |shareholder|
      if shareholder["id"] == @shareholder.id

      @ownership_over_time.push(shareholder["ownership_percentage"])

      end
      end
      end
      return @ownership_over_time
      end


      I then call this method in my view which successfully retrieves the correct values however they are not structured in any way:



      ["Event 1 ", "2018-11-19", "0.666666666666667", "Event 2 ", "2018-11-19", "0.333333333333333", "4th event ", "2018-11-19", "0.315789473684211"]


      What I'd like to do now though is construct my hash so that each separate snapshot event contains a name, date and ownership_percentage.



      Perhaps something like this:



      ownership_over_time = [
      {
      event_name = "Event 1" #parsed_snapshot["event"]["name"]
      event_date = "20180202" #parsed_snapshot["event"]["date"]
      ownership_percentage = 0.37 #shareholder["ownership_percentage"]
      },
      {
      event_name = "Event 2" #parsed_snapshot["event"]["name"]
      event_date = "20180501" #parsed_snapshot["event"]["date"]
      ownership_percentage = 0.60 #shareholder["ownership_percentage"]
      }
      ]


      My challenge though is that the ["event"]["name"] an ["event"]["date"] attributes I need to fetch when looping over my snapshots i.e. the first loop (.each do |snapshot|) whereas I get my ownership_percentage when looping over shareholders - the second loop (.each do |shareholder|).



      So my question is - how can I build this hash in "two" places so I can return the hash with the 3 attributes?



      Appreciative of guidance/help - thank you!







      ruby-on-rails






      share|improve this question















      share|improve this question













      share|improve this question




      share|improve this question








      edited Nov 22 at 16:30

























      asked Nov 22 at 15:54









      JP89

      8118




      8118
























          1 Answer
          1






          active

          oldest

          votes

















          up vote
          1
          down vote



          accepted










          You have to create a new hash for the object and append that hash to the array of objects you are creating.



            def fetch_ownership_over_time(shareholder, captable)

          @shareholder = Shareholder.find(shareholder.id)
          @captable = Captable.find(captable.id)
          @company = @captable.company.id
          @ownership_over_time =

          @captable.events.collect(&:snapshot).each do |snapshot|
          parsed_snapshot = JSON.parse(snapshot)
          shareholder = parsed_snapshot['shareholders'].select { |s| s['id'] == @shareholder.id }.first

          local_snapshot = {
          'event_name' => parsed_snapshot['event']['name'],
          'event_date' => parsed_snapshot['event']['date'],
          'ownership_percentage' => shareholder.try(:, "ownership_percentage") || 0
          }

          @ownership_over_time.push local_snapshot
          end
          return @ownership_over_time
          end


          Notice that I changed your second loop to a select. As you currently have it, you risk on pushing two percentages if the id is found twice.



          EDIT:



          Added functionality to use a default value if no shareholder is found.






          share|improve this answer























          • Great solution! Thank you!
            – JP89
            Nov 22 at 17:05






          • 1




            Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
            – byrdEmmanuel
            Nov 22 at 17:07










          • For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
            – JP89
            Nov 22 at 17:09










          • One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
            – JP89
            Nov 22 at 17:13








          • 1




            Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
            – byrdEmmanuel
            Nov 22 at 17:18













          Your Answer






          StackExchange.ifUsing("editor", function () {
          StackExchange.using("externalEditor", function () {
          StackExchange.using("snippets", function () {
          StackExchange.snippets.init();
          });
          });
          }, "code-snippets");

          StackExchange.ready(function() {
          var channelOptions = {
          tags: "".split(" "),
          id: "1"
          };
          initTagRenderer("".split(" "), "".split(" "), channelOptions);

          StackExchange.using("externalEditor", function() {
          // Have to fire editor after snippets, if snippets enabled
          if (StackExchange.settings.snippets.snippetsEnabled) {
          StackExchange.using("snippets", function() {
          createEditor();
          });
          }
          else {
          createEditor();
          }
          });

          function createEditor() {
          StackExchange.prepareEditor({
          heartbeatType: 'answer',
          convertImagesToLinks: true,
          noModals: true,
          showLowRepImageUploadWarning: true,
          reputationToPostImages: 10,
          bindNavPrevention: true,
          postfix: "",
          imageUploader: {
          brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
          contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
          allowUrls: true
          },
          onDemand: true,
          discardSelector: ".discard-answer"
          ,immediatelyShowMarkdownHelp:true
          });


          }
          });














          draft saved

          draft discarded


















          StackExchange.ready(
          function () {
          StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53434535%2fadding-values-to-a-hash-within-over-multiple-each-loops%23new-answer', 'question_page');
          }
          );

          Post as a guest















          Required, but never shown

























          1 Answer
          1






          active

          oldest

          votes








          1 Answer
          1






          active

          oldest

          votes









          active

          oldest

          votes






          active

          oldest

          votes








          up vote
          1
          down vote



          accepted










          You have to create a new hash for the object and append that hash to the array of objects you are creating.



            def fetch_ownership_over_time(shareholder, captable)

          @shareholder = Shareholder.find(shareholder.id)
          @captable = Captable.find(captable.id)
          @company = @captable.company.id
          @ownership_over_time =

          @captable.events.collect(&:snapshot).each do |snapshot|
          parsed_snapshot = JSON.parse(snapshot)
          shareholder = parsed_snapshot['shareholders'].select { |s| s['id'] == @shareholder.id }.first

          local_snapshot = {
          'event_name' => parsed_snapshot['event']['name'],
          'event_date' => parsed_snapshot['event']['date'],
          'ownership_percentage' => shareholder.try(:, "ownership_percentage") || 0
          }

          @ownership_over_time.push local_snapshot
          end
          return @ownership_over_time
          end


          Notice that I changed your second loop to a select. As you currently have it, you risk on pushing two percentages if the id is found twice.



          EDIT:



          Added functionality to use a default value if no shareholder is found.






          share|improve this answer























          • Great solution! Thank you!
            – JP89
            Nov 22 at 17:05






          • 1




            Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
            – byrdEmmanuel
            Nov 22 at 17:07










          • For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
            – JP89
            Nov 22 at 17:09










          • One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
            – JP89
            Nov 22 at 17:13








          • 1




            Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
            – byrdEmmanuel
            Nov 22 at 17:18

















          up vote
          1
          down vote



          accepted










          You have to create a new hash for the object and append that hash to the array of objects you are creating.



            def fetch_ownership_over_time(shareholder, captable)

          @shareholder = Shareholder.find(shareholder.id)
          @captable = Captable.find(captable.id)
          @company = @captable.company.id
          @ownership_over_time =

          @captable.events.collect(&:snapshot).each do |snapshot|
          parsed_snapshot = JSON.parse(snapshot)
          shareholder = parsed_snapshot['shareholders'].select { |s| s['id'] == @shareholder.id }.first

          local_snapshot = {
          'event_name' => parsed_snapshot['event']['name'],
          'event_date' => parsed_snapshot['event']['date'],
          'ownership_percentage' => shareholder.try(:, "ownership_percentage") || 0
          }

          @ownership_over_time.push local_snapshot
          end
          return @ownership_over_time
          end


          Notice that I changed your second loop to a select. As you currently have it, you risk on pushing two percentages if the id is found twice.



          EDIT:



          Added functionality to use a default value if no shareholder is found.






          share|improve this answer























          • Great solution! Thank you!
            – JP89
            Nov 22 at 17:05






          • 1




            Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
            – byrdEmmanuel
            Nov 22 at 17:07










          • For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
            – JP89
            Nov 22 at 17:09










          • One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
            – JP89
            Nov 22 at 17:13








          • 1




            Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
            – byrdEmmanuel
            Nov 22 at 17:18















          up vote
          1
          down vote



          accepted







          up vote
          1
          down vote



          accepted






          You have to create a new hash for the object and append that hash to the array of objects you are creating.



            def fetch_ownership_over_time(shareholder, captable)

          @shareholder = Shareholder.find(shareholder.id)
          @captable = Captable.find(captable.id)
          @company = @captable.company.id
          @ownership_over_time =

          @captable.events.collect(&:snapshot).each do |snapshot|
          parsed_snapshot = JSON.parse(snapshot)
          shareholder = parsed_snapshot['shareholders'].select { |s| s['id'] == @shareholder.id }.first

          local_snapshot = {
          'event_name' => parsed_snapshot['event']['name'],
          'event_date' => parsed_snapshot['event']['date'],
          'ownership_percentage' => shareholder.try(:, "ownership_percentage") || 0
          }

          @ownership_over_time.push local_snapshot
          end
          return @ownership_over_time
          end


          Notice that I changed your second loop to a select. As you currently have it, you risk on pushing two percentages if the id is found twice.



          EDIT:



          Added functionality to use a default value if no shareholder is found.






          share|improve this answer














          You have to create a new hash for the object and append that hash to the array of objects you are creating.



            def fetch_ownership_over_time(shareholder, captable)

          @shareholder = Shareholder.find(shareholder.id)
          @captable = Captable.find(captable.id)
          @company = @captable.company.id
          @ownership_over_time =

          @captable.events.collect(&:snapshot).each do |snapshot|
          parsed_snapshot = JSON.parse(snapshot)
          shareholder = parsed_snapshot['shareholders'].select { |s| s['id'] == @shareholder.id }.first

          local_snapshot = {
          'event_name' => parsed_snapshot['event']['name'],
          'event_date' => parsed_snapshot['event']['date'],
          'ownership_percentage' => shareholder.try(:, "ownership_percentage") || 0
          }

          @ownership_over_time.push local_snapshot
          end
          return @ownership_over_time
          end


          Notice that I changed your second loop to a select. As you currently have it, you risk on pushing two percentages if the id is found twice.



          EDIT:



          Added functionality to use a default value if no shareholder is found.







          share|improve this answer














          share|improve this answer



          share|improve this answer








          edited Nov 22 at 17:33

























          answered Nov 22 at 17:04









          byrdEmmanuel

          807215




          807215












          • Great solution! Thank you!
            – JP89
            Nov 22 at 17:05






          • 1




            Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
            – byrdEmmanuel
            Nov 22 at 17:07










          • For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
            – JP89
            Nov 22 at 17:09










          • One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
            – JP89
            Nov 22 at 17:13








          • 1




            Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
            – byrdEmmanuel
            Nov 22 at 17:18




















          • Great solution! Thank you!
            – JP89
            Nov 22 at 17:05






          • 1




            Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
            – byrdEmmanuel
            Nov 22 at 17:07










          • For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
            – JP89
            Nov 22 at 17:09










          • One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
            – JP89
            Nov 22 at 17:13








          • 1




            Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
            – byrdEmmanuel
            Nov 22 at 17:18


















          Great solution! Thank you!
          – JP89
          Nov 22 at 17:05




          Great solution! Thank you!
          – JP89
          Nov 22 at 17:05




          1




          1




          Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
          – byrdEmmanuel
          Nov 22 at 17:07




          Glad it suits your needs, perhaps there is a more efficient way to solve it or a more stylish way to write it, but I'm sure you can take it from here.
          – byrdEmmanuel
          Nov 22 at 17:07












          For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
          – JP89
          Nov 22 at 17:09




          For sure - I've been pondering how best to solve this but will push on from here and try refactor a little. Thank you again!
          – JP89
          Nov 22 at 17:09












          One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
          – JP89
          Nov 22 at 17:13






          One thing I've run into is that we get a crash if the ownership_percentage is null or none exist. Do you think I should just wrap the entire local_snapshot in an unless not null so that we skip creating that snapshot if so?
          – JP89
          Nov 22 at 17:13






          1




          1




          Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
          – byrdEmmanuel
          Nov 22 at 17:18






          Or you could give a default value for it when creating the local_snapshot. As it is a percentage, a persona having 0 is probably what you want when none is found: 'ownership_percentage' => shareholder['ownership_percentage'] || 0
          – byrdEmmanuel
          Nov 22 at 17:18




















          draft saved

          draft discarded




















































          Thanks for contributing an answer to Stack Overflow!


          • Please be sure to answer the question. Provide details and share your research!

          But avoid



          • Asking for help, clarification, or responding to other answers.

          • Making statements based on opinion; back them up with references or personal experience.


          To learn more, see our tips on writing great answers.





          Some of your past answers have not been well-received, and you're in danger of being blocked from answering.


          Please pay close attention to the following guidance:


          • Please be sure to answer the question. Provide details and share your research!

          But avoid



          • Asking for help, clarification, or responding to other answers.

          • Making statements based on opinion; back them up with references or personal experience.


          To learn more, see our tips on writing great answers.




          draft saved


          draft discarded














          StackExchange.ready(
          function () {
          StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53434535%2fadding-values-to-a-hash-within-over-multiple-each-loops%23new-answer', 'question_page');
          }
          );

          Post as a guest















          Required, but never shown





















































          Required, but never shown














          Required, but never shown












          Required, but never shown







          Required, but never shown

































          Required, but never shown














          Required, but never shown












          Required, but never shown







          Required, but never shown







          Popular posts from this blog

          What visual should I use to simply compare current year value vs last year in Power BI desktop

          How to ignore python UserWarning in pytest?

          Alexandru Averescu