How to get the MATCH value from MAP - stream

I'm trying to figure out how to get the matching value and store in a string variable and here is what I have done:
For the sample purpose I have created the following:
Map<Attachment, String> mapattach = new HashMap<Attachment, String>();
Attachment a1 = new Attachment();
a1.setId("one1");
a1.setName("one");
a1.setUrl("http://1.com");
Attachment a2 = new Attachment();
a2.setId("two2");
a2.setName("two");
a2.setUrl("http://2.com");
Attachment a3 = new Attachment();
a3.setId("three3");
a3.setName("three");
a3.setUrl("http://3.com");
mapattach.put(a1, "one1");
mapattach.put(a2, "two22");
mapattach.put(a3, "three33");
//java stream
//it will match only one item and it returns
String matchFound = mapattach.entrySet().stream()
.filter( f -> recordIds.contains(f.getKey().getId()))
.findFirst().toString();
The above code returns the string of a record:
result:
Optional[class Attachment {
name: one
id: one1
mimeType: null
url: http://1.com
referenceId: null }=one1]
BUT what I want is just url how would I do?

You were almost there, this should do the trick:
Optional<String> optionalUrl = mapattach.entrySet().stream()
.filter(f -> recordIds.contains(f.getKey().getId()))
.findFirst()
.map(attachmentStringEntry -> attachmentStringEntry.getKey().getUrl());
urlMatchFound = optionalUrl.get(); // remember that it might not be present.

Related

accessing object values using variable as a key

I'm trying to access a class value by using a variable previously defined in dart, but I keep getting the error the operator [] isn't defined for the class
In Javascript I would access an object value using a variable like this:
let movie = {
movieTitle : 'Toy Story',
actor: 'Tom Hanks'
}
let actorName = 'actor';
console.log(movie[actorName]); // <- what I'm trying to replicate in dart
// expected output: Tom Hanks
Here is what I've tried and is throwing that error
class Movie {
String name;
String actor;
String producer;
}
void main() {
var movieTitle = new Movie();
movieTitle.name = 'Toy Story';
movieTitle.actor = 'Tom Hanks';
print(movieTitle.actor); <- prints out Tom Hanks as expected
var actorName = 'actor';
print(movieTitle[actorName]); <- throws error
}
I expect to be able to use a variable on the fly to access the value.
A trivial use case for me would be if I had a a list of Movie classes, where some actors and producers are null, I would like to filter on either non null actors or producer with a function like so:
List values = movieList.where((i) => i.actor != "null").toList(); // returns all Movies in movieList where the actor value isn't the string "null"
var actorIsNull = 'actor';
List values = movieList.where((i) => i[actorisNull] != "null").toList(); // throws error
You can createn a toMap() function in your Movie class and access properties using [] operator
class Movie {
String name;
String actor;
String producer;
Map<String, dynamic> toMap() {
return {
'name': name,
'actor' : actor,
'producer' : producer,
};
}
}
Now Movie class properties can be accessed as:
Movie movie = Movie();
movie.toMap()['name'];
You cannot access class members by a string containing their name. (Except with mirrors - outside the scope of this answer.)
You could remove the class altogether and just use a Map<String, String>.
Map<String, String> movie = {
'movieTitle': 'Toy Story',
'actor': 'Tom Hanks',
}
You could add some bool methods on the class.
bool hasNoActor() => actor == null;
...
List values = movieList.where((m) => !m.hasNoActor()).toList();
Or, you could pass a lambda to your mapper.
Movie movieTitle = Movie()
..name = 'Toy Story'
..actor = 'Tom Hanks';
Function hasActor = (Movie m) => m.actor != null;
List values = movieList.where(hasActor).toList();

Groovy: Dynamic nested properties [duplicate]

I am wondering if I can pass variable to be evaluated as String inside gstring evaluation.
simplest example will be some thing like
def var ='person.lName'
def value = "${var}"
println(value)
I am looking to get output the value of lastName in the person instance. As a last resort I can use reflection, but wondering there should be some thing simpler in groovy, that I am not aware of.
Can you try:
def var = Eval.me( 'new Date()' )
In place of the first line in your example.
The Eval class is documented here
edit
I am guessing (from your updated question) that you have a person variable, and then people are passing in a String like person.lName , and you want to return the lName property of that class?
Can you try something like this using GroovyShell?
// Assuming we have a Person class
class Person {
String fName
String lName
}
// And a variable 'person' stored in the binding of the script
person = new Person( fName:'tim', lName:'yates' )
// And given a command string to execute
def commandString = 'person.lName'
GroovyShell shell = new GroovyShell( binding )
def result = shell.evaluate( commandString )
Or this, using direct string parsing and property access
// Assuming we have a Person class
class Person {
String fName
String lName
}
// And a variable 'person' stored in the binding of the script
person = new Person( fName:'tim', lName:'yates' )
// And given a command string to execute
def commandString = 'person.lName'
// Split the command string into a list based on '.', and inject starting with null
def result = commandString.split( /\./ ).inject( null ) { curr, prop ->
// if curr is null, then return the property from the binding
// Otherwise try to get the given property from the curr object
curr?."$prop" ?: binding[ prop ]
}

Set F# list as null for serialisation

I'm using F# alongside a JSON data-store making use of the JSON.NET library. I'm trying to utilise F# structures and types where possible and have run into the following issue. Say I wish to store the following data structure,
type A = {
id : int
name : string
posts : string list
}
Creation works fine, but to update just the stored name field I need to send a JSON record that omits the posts field. Using the empty list won't work as the persistence system will assume that I wish to replace the existing posts with an empty list and thus overwrite them. From the JSON.NET docs I've read a field can be omitted from serialisation by setting it to null,
let updatedEntry = { id : 0, name : "Fred", posts = null }
However the F# compiler will give an error stating that the type list can not be set to null. Is there anyway to accomplish this from within F#, perhaps an attribute I'm unaware of? Thanks
There are two ways you could do this easily:
Option 1
Use the System.Collections.Generic.List type, which can be null:
> type A = {id: int; name:string; posts: System.Collections.Generic.List<string> };;
type A =
{id: int;
name: string;
posts: System.Collections.Generic.List<string>;}
> let a = {id=5; name="hello"; posts=null};;
val a : A = {id = 5;
name = "hello";
posts = null;}
Option 2
The other, more idiomatic way, would be to use the Option type:
> type A = {id: int; name:string; posts: string list option };;
type A =
{id: int;
name: string;
posts: string list option;}
> let a = {id=5; name="there"; posts=None};;
val a : A = {id = 5;
name = "there";
posts = null;}
Note that you'd compare the posts member to None rather than null.
Handy reading: Option types
Edit
(After some searching & experimentation) you could use boxing to still use F# types as the values:
> type A = {id: int; name:string; posts: System.Object };;
type A =
{id: int;
name: string;
posts: Object;}
> let a = {id=5; name="foo"; posts=null};;
val a : A = {id = 5;
name = "foo";
posts = null;}
> let b = {id=6; name="bar"; posts=(box [])};;
val b : A = {id = 6;
name = "bar";
posts = [];}
But I'd stick with the Option type, personally

Use GLib.HashTable in Genie

How can I access GLib.HashTable in Genie? I am trying to write a handler method for libsoup HTTP server. The query parameter is a GLib.HashTable. When I try to access query e.g. with
def search_handler (server : Soup.Server, msg : Soup.Message, path : string,
query : GLib.HashTable?, client : Soup.ClientContext)
response_text : string = null
if query is not null && query.contains("expr")
response_text = get_search(query.get("expr"))
I got the error:
error: missing generic type arguments
response_text = get_search(query.get("expr"))
^^^^^
The only way I found is to make a new HashTable object:
p : GLib.HashTable of string, string = query
expr : string = p.get("expr")
What is the right way to handle this?
My be you can try with : dict of string,string
var d = new dict of string,string
d["one"]="1"
d["two"]="2"
print "%s",d["one"]
something like this
[indent=4]
init
var h = new HashTable of string, int (str_hash, str_equal)
h["foo"] = 123
h["bar"] = 456
foo ("foo", h)
def foo (key: string, hash: HashTable of string, int)
// PUT HASHTABLE IN THE END
if hash.contains (key)
stdout.printf ("%s => %i", key, hash[key])

Combining extension methods

I'm trying to write 2 extension methods to handle Enum types. One to use the description attribute to give some better explanation to the enum options and a second method to list the enum options and their description to use in a selectlist or some kind of collection.
You can read my code up to now here:
<Extension()> _
Public Function ToDescriptionString(ByVal en As System.Enum) As String
Dim type As Type = en.GetType
Dim entries() As String = en.ToString().Split(","c)
Dim description(entries.Length) As String
For i = 0 To entries.Length - 1
Dim fieldInfo = type.GetField(entries(i).Trim())
Dim attributes() = DirectCast(fieldInfo.GetCustomAttributes(GetType(DescriptionAttribute), False), DescriptionAttribute())
description(i) = If(attributes.Length > 0, attributes(0).Description, entries(i).Trim())
Next
Return String.Join(", ", description)
End Function
<Extension()> _
Public Function ToListFirstTry(ByVal en As System.Enum) As IEnumerable
Dim type As Type = en.GetType
Dim items = From item In System.Enum.GetValues(type) _
Select New With {.Value = item, .Text = item.ToDescriptionString}
Return items
End Function
<Extension()> _
Public Function ToListSecondTry(ByVal en As System.Enum) As IEnumerable
Dim list As New Dictionary(Of Integer, String)
Dim enumValues As Array = System.Enum.GetValues(en.GetType)
For Each value In enumValues
list.Add(value, value.ToDescriptionString)
Next
Return list
End Function
So my problem is both extension methods don't work that well together. The methods that converts the enum options to an ienumerable can't use the extension method to get the description.
I found all kind of examples to do one of both but never in combination with each other. What am I doing wrong? I still new to these new .NET 3.5 stuff.
The problem is that Enum.GetValues just returns a weakly typed Array.
Try this:
Public Function ToListFirstTry(ByVal en As System.Enum) As IEnumerable
Dim type As Type = en.GetType
Dim items = From item In System.Enum.GetValues(type).Cast(Of Enum)() _
Select New With {.Value = item, .Text = item.ToDescriptionString}
Return items
End Function
(It looks like explicitly typed range variables in VB queries don't mean the same thing as in C#.)

Resources