jeudi 31 août 2023

Swift 5 Comparing Object properties

I'm trying to compare two objects to check which properties were updated. I'm using Mirror to list the properties and try the comparison. Code is:

                let mirrorLote = Mirror(reflecting: l)
                let mirrorLoteUpd = Mirror(reflecting: lUpd)
                
                mirrorLote.children.forEach { child in
                    if (child.label != "id") {
                        mirrorLoteUpd.children.forEach { childUpd in
                            if (child.label == childUpd.label && child.value != childUpd.value){
                                addUpdatesDB(prop: child.label, val: childUpd.value)
                            }
                        }
                    }
                }

I'm getting the following error: "Type 'Any' cannot conform to 'RawRepresentable'" when trying to compare the values (child.value != childUpd.value).

Any ideas on how can I resolve this? Thanks!!





Why does the reflections library not work in a Spring Boot application?

I'm using org.reflections:reflections to find annotated classes on the classpath within a Spring Boot application. When running the app from the IDE, everything works fine. But when I build the FAT-JAR and run it directly, it can't find some classes. Here's a simplified version of my code:

// packagePrefixes is an array of strings
Reflections reflections = new Reflections(packagePrefixes, Scanners.TypesAnnotated);

for (Class<?> clazz : reflections.getTypesAnnotatedWith(Resource.BaseClass.class)) {
    // This works, it'll iterate through this
}

for (Class<?> clazz : reflections.getTypesAnnotatedWith(Listener.class)) {
    // This doesn't work, it won't iterate through this
}

Both annotations are annotated with

@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)

I already tried using precise packages so that the library won't need to iterate recursively.

Does anyone know what the problem is here? Thanks for your help :)





lundi 28 août 2023

Why the result of descriptor.field_count() is different?

I'm using protobuf in Qt platform. function A and B are slot functions:

function A : void MainWindow::pushButton_load_clicked();
function B : void MainWindow::listWidget_LBM_itemClicked(QListWidgetItem *item);
dic : QHash<QString, const Message*> dic;

In function A, I store the pointer to Message to a hashtable.

for (auto message_ptr : res)
{
   // ...
   dic[funcid] = message_ptr;
}

In function B, I get the pointer to Message and use protobuf API to get the number of fields in the Message.

// ...
if(dic.find(funcid) == dic.end())
{
   qDebug() << "funcid " << funcid << " does not exist in dic" << endl;
   return;
}
const Message* message_ptr = dic[funcid];
const Descriptor* desc = message_ptr->GetDescriptor();
qDebug() << "funcid is : " << funcid << "desc->field_count() : " << desc->field_count() << endl;

But when I call function B for several times, the result of descriptor->field_count() is different. the output is:

funcid is :  "30001" desc->field_count() :  0 

funcid is :  "30007" desc->field_count() :  6881390 

the correct answer is 16 and 5.

I have tried to test whether the two pointers to Descriptor of one Message in function A and function B are the same. The answer is yes.

const Message* m1,m2,m3;
const Descriptor* d1,*d2,*d3;
int cnt = 0;
int f1, f2, f3;

function A:
dic[funcid] = message_ptr;
if(cnt == 0)
{
     m1 = message_ptr;
     d1 = m1->GetDescriptor();
     f1 = d1->field_count();
     ++cnt;
}
else if(cnt == 1)
{
     m2 = message_ptr;
     d2 = m2->GetDescriptor();
     f2 = d2->field_count();
     ++cnt;
}
else
{
     m3 = message_ptr;
     d3 = m3->GetDescriptor();
     f3 = d3->field_count();
}

function B:
const Message * message_ptr = dic[funcid];
if(funcid == "30007")
{
    auto d = message_ptr->GetDescriptor();
    if(message_ptr == m1)
        qDebug() << "equals m1" << endl;
    else
        qDebug() << "not equals m1" << endl;
    if(d == d1)
        qDebug() << "equals d1" << endl;
    else
        qDebug() << "not equals d1" << endl;
    if(d->field_count() == f1)
        qDebug() << "equals f1" << endl;
    else
        qDebug() << "not equals f1" << endl;
}
else if(funcid == "30001")
{
    auto d = message_ptr->GetDescriptor();
    if(message_ptr == m2)
        qDebug() << "equals m2" << endl;
    else
        qDebug() << "not equals m2" << endl;
    if(message_ptr->GetDescriptor() == d2)
        qDebug() << "equals d2" << endl;
    else
        qDebug() << "not equals d2" << endl;
    if(d->field_count() == f2)
        qDebug() << "equals f2" << endl;
    else
        qDebug() << "not equals f2" << endl;
}
else
{
    auto d = message_ptr->GetDescriptor();
    if(message_ptr == m3)
        qDebug() << "equals m3" << endl;
    else
        qDebug() << "not equals m3" << endl;
    if(message_ptr->GetDescriptor() == d3)
        qDebug() << "equals d3" << endl;
    else
        qDebug() << "not equals d3" << endl;
    if(d->field_count() == f3)
        qDebug() << "equals f3" << endl;
    else
        qDebug() << "not equals f3" << endl;
}

the output is :

equals m1 

equals d1 

not equals f1 

equals m2 

equals d2 

not equals f2 

equals m3 

equals d3 

equals f3 

Does anyone know the reason? Thanks in advance.

I'm expecting to get the correct result of descriptor->field_count() in function B.





Does PHP8 Reflection more bad performance versus PHP7 without reflection

I have re write my code from old php 7.4 scripts. And i see my code be more slower than old version My old models export data from method toArray And his representation was like that

public function toArray()
{
   return [
      "id" => $this->id;
      "name" => $this->name;
      //And many other values
   ]
}

But now, with PHP 8, i have use reflection object to serialize my object. That take something like :

class MyModel extends Model
{
   #[AttributeExport]
   private int $id;

   #[AttributeExport]
   private string $name;
}

//In Model

abstract Model implement JsonSerialize
{
   function jsonSerialize(): array
   {
      //Here i get all my attributes from current class
      //And i construct array to return
   }
}

I may be mistakenly thinking that the problem may come from there. But do you think that on a large volume of data, this strategy can have an impact?

I used more abstract class compared to the old version to avoid code duplication. Dont know if that can impact too





samedi 26 août 2023

Can I dynamically get an argument name of a method (not parameter name)?

Here's code

    public Configuration setProperty(int someSpecificProperty) {
        MyAppUtil.requirePositive(someSpecificProperty, "someSpecificProperty");
        this.someSpecificProperty = someSpecificProperty;
        return this;
    }
// MyAppUtil
    static void requirePositive(int property, String propertyName) {
        if (property <= 0) {
            throw new IllegalPropertyException(propertyName, PropertyIssue.NON_POSITIVE);
        }
    }
public class IllegalPropertyException extends RuntimeException {
    private static final String FORMAT = "%s value is invalid: should be %s";
    public IllegalPropertyException(String propertyName, PropertyIssue propertyIssue) {
        super(String.format(FORMAT, propertyName, propertyIssue.whatItShouldBeInstead()));
    }

    @RequiredArgsConstructor
    public enum PropertyIssue {
        NULL("not null"), EMPTY("not empty"), NON_POSITIVE("greater than zero");

        private final String whatItShouldBeInstead;

        String whatItShouldBeInstead() {
            return whatItShouldBeInstead;
        }
    }
}

Notice how I pass both a property and that property's name. I am wondering whether I could get that information about the argument name dynamically so that the client (or rather, I) don't have to pass it manually each time. It would've been nice if I could call the requrePositive() method like this (and MyAppUtil figured out the argument name itself):

    public Configuration setSpecificProperty(int someSpecificProperty) {
        MyAppUtil.requirePositive(someSpecificProperty);
        this.someSpecificProperty = someSpecificProperty;
        return this;
    }

Is there a way to do that?





How to pass a method name (safely) in Go

Is it possible to pass a method name in a safe manner? Currently I'm simply passing the method name as a string and match it using reflect but I wonder if it would be possible to pass it in a more safe manner(i.e as below) to prevent misspelling it or code getting out of sync (i.e. method name being renamed).

 package main

func Exists[T any](method any) string {
    // we extract the method name from the method/function itself. Impossible?

    // return the method name if it exists
    return ""
}

func main() {
    //we pass the method itself instead of its name (i.e. "Hello")
    m := Exists[X](X.Hello)
    if m != "Hello" {
        panic("expected  Hello")
    }
}

type X struct{}

func (X) Hello()   {}
func (X) GoodBye() {}

Play me





vendredi 25 août 2023

Get implementer class type

I have the below code

public abstract class abstract1
{
    public void Test1()
    {
        // Do something
    }
}

public class class1 : abstract1
{
}

public class Class1Test
{
    public void InvokeTest1()
    {
        Class1 c1 = new Class1();
        c1.Test1();
    }
}

How can I get that Test1 method invoked from Class1 then abstract1 for logging purposes?

Thanks,